Jak korzystać z Select2 z JSON za pośrednictwem żądania Ajax?


88

Mój Select2 3.4.5 nie działa z danymi JSON.

Oto moje pole wprowadzania w HTML:

<input class='form-control col-lg-5 itemSearch' type='text' placeholder='select item' />

… I mój JavaScript

$(".itemSearch").select2({
    placeholder: "Search for an Item",
    minimumInputLength: 2,
    ajax: {
        url: "/api/productSearch",
        dataType: 'json',
        quietMillis: 100,
        data: function (term, page) {
            return {
                option: term
            };
        },
        results: function (data, page) {
            var more = (page * 10) < data.total;
            return {
                results: data.itemName,
                more: more
            };
        }
    },
    formatResult: function (data, term) {
        return data;
    },
    formatSelection: function (data) {
        return data;
    },
    dropdownCssClass: "bigdrop",
    escapeMarkup: function (m) {
        return m;
    }
});

Stworzyłem API z Laravel 4, które zwraca wartość za każdym razem, gdy piszę cokolwiek w moim polu tekstowym.

Oto wynik, jeśli wpiszę „test” w moim polu tekstowym:

[{"itemName":"Test item no. 1","id":5},
{"itemName":"Test item no. 2","id":6},
{"itemName":"Test item no. 3","id":7},
{"itemName":"Test item no. 4","id":8},
{"itemName":"Test item no. 5","id":9},
{"itemName":"Test item no. 6","id":10},
{"itemName":"Test item no. 7","id":11}]

Nie mogę dodać wyniku do listy rozwijanej Select2. Myślę formatSelectioni formatResultpowodują problem, ponieważ nie wiem, jaki parametr powinien być na nim umieszczony. Nie wiem, skąd wziąć te parametry, takie jak kontener, obiekt i zapytanie oraz wartości, które powinny zwracać, czy też moja odpowiedź JSON jest nieprawidłowa?

Odpowiedzi:


110

Tutaj masz przykład

$("#profiles-thread").select2({
    minimumInputLength: 2,
    tags: [],
    ajax: {
        url: URL,
        dataType: 'json',
        type: "GET",
        quietMillis: 50,
        data: function (term) {
            return {
                term: term
            };
        },
        results: function (data) {
            return {
                results: $.map(data, function (item) {
                    return {
                        text: item.completeName,
                        slug: item.slug,
                        id: item.id
                    }
                })
            };
        }
    }
});

To całkiem proste


2
Dzięki za sugestię do $ .map
tacos_tacos_tacos,

Czy możesz wyjaśnić parametr „slug”?
IcedDante

item jest obiektem z właściwościami completeName, slug i id. To tylko przykład, kopiuj i wklej.
Tolo Palmer

2
Ślimak to aktualna własność przedmiotu, twojego przedmiotu, dodałem to jak widać jak dodać dodatkowe parametry;)
Tolo Palmer

4
Otrzymuję ten błąd jquery.min.js: 2 Uncaught TypeError: Nie można odczytać właściwości „length” o wartości null, gdy mój serwer nie zwraca żadnego wyniku.
Soptareanu Alex

109

dla select2 v4.0.0 nieco inaczej

$(".itemSearch").select2({
    tags: true,
    multiple: true,
    tokenSeparators: [',', ' '],
    minimumInputLength: 2,
    minimumResultsForSearch: 10,
    ajax: {
        url: URL,
        dataType: "json",
        type: "GET",
        data: function (params) {

            var queryParameters = {
                term: params.term
            }
            return queryParameters;
        },
        processResults: function (data) {
            return {
                results: $.map(data, function (item) {
                    return {
                        text: item.tag_value,
                        id: item.tag_id
                    }
                })
            };
        }
    }
});

8
Nie mogę tego uruchomić ... :( Brak połączeń z serwerem.
Simanas

Zadziałało dzięki, błąd, który popełniłem, polegał na nieprawidłowym mapowaniu idi textkluczowych wartościach.
Ja8zyjits

18

W wersji 4.0.2 nieco inaczej Just in processResultsi in result:

    processResults: function (data) {
        return {
            results: $.map(data.items, function (item) {
                return {
                    text: item.tag_value,
                    id: item.tag_id
                }
            })
        };
    }

Należy dodać data.itemsw result. itemsto nazwa Json:

{
  "items": [
    {"id": 1,"name": "Tetris","full_name": "s9xie/hed"},
    {"id": 2,"name": "Tetrisf","full_name": "s9xie/hed"}
  ]
}

1
Jeśli usunę itemsz pola, data.itemsnie będę musiał dodawać itemsatrybutu w odpowiedzi, prawda? ;)
Yana Agun Siswanto

1
@bekicot tak, po prostu określ tylko, $.map(data, function (item) czy twój json jest tablicą:[ {"id": 1,"text": "One"}, {"id": 2,"text": "Two"} ]
Tantowi Mustofa

2
Waliłem głową o ścianę i to wyjaśniło sprawę. Dziękuję, bardzo brakuje dokumentacji dla select2.
Neil B.

11

Oto mój przykład, który zawiera -> Flaga kraju, miasto, stan, kraj.

Oto mój wynik.

wprowadź opis obrazu tutaj

Dołącz te dwa pliki Cdn js lub łącza.

<link href="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.10/css/select2.min.css" rel="stylesheet" />
<script src="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.10/js/select2.min.js"></script>

js

//for apend flag of country.

function formatState (state) {
    console.log(state);
    if (!state.id) {
      return state.text;
    }
    var baseUrl = "admin/images/flags";
    var $state = $(
      '<span><img src="'+baseUrl+ '/' + state.contryflage.toLowerCase() + '.png"  class="img-flag" /> ' +state.text+ '</span>'
    );
    return $state;
  };


$(function(){
    $("#itemSearch").select2({
    minimumInputLength: 2,
    templateResult: formatState, //this is for append country flag.
    ajax: {
        url: URL,
        dataType: 'json',
        type: "POST",
        data: function (term) {
            return {
                term: term
            };
        },
        processResults: function (data) {
            return {
                results: $.map(data, function (item) {
                    return {
                        text: item.name+', '+item.state.name+', '+item.state.coutry.name,
                        id: item.id,
                        contryflage:item.state.coutry.sortname
                    }
                })
            };
        }

    }
});

Oczekiwana odpowiedź JSON.

[
   {
      "id":7570,
      "name":"Brussels",
      "state":{
         "name":"Brabant",
         "coutry":{
            "sortname":"BE",
            "name":"Belgium",

         }
      }
   },
   {
      "id":7575,
      "name":"Brussels",
      "state":{
         "name":"Brabant Wallon",
         "coutry":{
            "sortname":"BE",
            "name":"Belgium",

         }
      }
   },
   {
      "id":7578,
      "name":"Brussel",
      "state":{
         "name":"Brussel",
         "coutry":{
            "sortname":"BE",
            "name":"Belgium",

         }
      }
   },

]

ale mylę się w `data: function (term) {return {term: term}; }, `
Vikas Katariya

6

W ten sposób naprawiłem swój problem, otrzymuję dane w zmiennej data i używając powyższych rozwiązań otrzymałem błąd could not load results. Musiałem inaczej przeanalizować wyniki w processResults.

searchBar.select2({
            ajax: {
                url: "/search/live/results/",
                dataType: 'json',
                headers : {'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content')},
                delay: 250,
                type: 'GET',
                data: function (params) {
                    return {
                        q: params.term, // search term
                    };
                },
                processResults: function (data) {
                    var arr = []
                    $.each(data, function (index, value) {
                        arr.push({
                            id: index,
                            text: value
                        })
                    })
                    return {
                        results: arr
                    };
                },
                cache: true
            },
            escapeMarkup: function (markup) { return markup; },
            minimumInputLength: 1
        });

1

Problemy mogą być spowodowane nieprawidłowym mapowaniem. Czy na pewno masz zestaw wyników w „danych”? W moim przykładzie kod zaplecza zwraca wyniki pod kluczem „items”, więc mapowanie powinno wyglądać następująco:

results: $.map(data.items, function (item) {
....
}

i nie:

 results: $.map(data, function (item) {
    ....
    }

1

Mój Ajax nigdy nie zostaje zwolniony, dopóki nie zapakuję całej rzeczy

setTimeout(function(){ .... }, 3000);

Używałem go w zamontowanej sekcji Vue. potrzebuje więcej czasu.


0

Jeśli żądanie AJAX nie zostanie uruchomione, sprawdź klasę select2 w elemencie select. Usunięcie klasy select2 rozwiąże ten problem.

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.