2015-11-16 9 views
6

Podążyłem za tutorialem this i zmodyfikowałem przykład, aby pasował do moich aktualnych potrzeb. To jest mój collections.js który znajduje się w moim libDlaczego pojawia się błąd podczas próby użycia pakietu źródłowego wyszukiwania Meteor?

Guides = new Mongo.Collection("guides"); 

Mam następujący kod w moim kontrolera po stronie klienta.

var options = { 
    keepHistory: 1000 * 60 * 5, 
    localSearch: true 
}; 

var fields = ['title']; 

GuideSearch = new SearchSource('guides', fields, options); 

Template.guide_list.helpers({ 
    getGuides: function() { 
     return GuideSearch.getData({ 
      transform: function (matchText, regExp) { 
       return matchText.replace(regExp, "<b>$&</b>") 
      } 
     }); 
    }, 

    isLoading: function() { 
     return GuideSearch.getStatus().loading; 
    } 
}); 


Template.guide_list.events({ 
    "keyup #title": _.throttle(function(e) { 
     var text = $(e.target).val().trim(); 
     GuideSearch.search(text); 
    }, 200) 
}); 

I to jak mój serwer kodu po stronie

SearchSource.defineSource('guides', function(searchText, options) { 
    if(searchText) { 
    var regExp = buildRegExp(searchText); 
    var selector = {title: regExp} 
    return Guides.find(selector, options).fetch(); 
    } else { 
    return Guides.find({}, options).fetch(); 
    } 
}); 

function buildRegExp(searchText) { 
    // this is a dumb implementation 
    var parts = searchText.trim().split(/[ \-\:]+/); 
    return new RegExp("(" + parts.join('|') + ")", "ig"); 
} 

z jakiegoś powodu, pojawia się następujący komunikat o błędzie podczas pisania coś w moim polu wejściowym

Exception in delivering result of invoking 'search.source': Meteor.makeErrorType/[email protected]://10.0.3.162:3000/packages/meteor.js?9730f4ff059088b3f7f14c0672d155218a1802d4:525:15 
[email protected]://10.0.3.162:3000/packages/ddp-client.js?250b63e6c919c5383a0511ee4efbf42bb70a650f:4625:23 
Connection/[email protected]://10.0.3.162:3000/packages/ddp-client.js?250b63e6c919c5383a0511ee4efbf42bb70a650f:3365:7 
._launchConnection/self.socket.onmessage/<@http://10.0.3.162:3000/packages/ddp-client.js?250b63e6c919c5383a0511ee4efbf42bb70a650f:2734:11 
[email protected]://10.0.3.162:3000/packages/underscore.js?46eaedbdeb6e71c82af1b16f51c7da4127d6f285:149:7 
._launchConnection/[email protected]://10.0.3.162:3000/packages/ddp-client.js?250b63e6c919c5383a0511ee4efbf42bb70a650f:2733:9 
[email protected]://10.0.3.162:3000/packages/ddp-client.js?250b63e6c919c5383a0511ee4efbf42bb70a650f:173:9 
[email protected]://10.0.3.162:3000/packages/ddp-client.js?250b63e6c919c5383a0511ee4efbf42bb70a650f:1158:5 
[email protected]://10.0.3.162:3000/packages/ddp-client.js?250b63e6c919c5383a0511ee4efbf42bb70a650f:1216:13 
SockJS.websocket/[email protected]://10.0.3.162:3000/packages/ddp-client.js?250b63e6c919c5383a0511ee4efbf42bb70a650f:1363:9 

To jest mój kod szablonu :

template(name="guide_list") 
    .format-properly 
     .container-fluid 
      .input-group#adv-search 
       .form-horizontal(role="form" method="POST" action="#") 
        .col-md-6 
         .form-group 
          label(for="contain") Guide title 
          input.form-control(type="text" id="title") 
        .col-md-6 
         .form-group 
          label(for="contain") Author 
          input.form-control(type="text" name="author") 
        .col-md-6 
         .form-group 
          label(for="hero") Select a hero 
          select.form-control(name="hero") 
           option(value="all" selected) All Heroes 
           option(value="Druid") Druid 
           option(value="Hunter") Hunter 
           option(value="Mage") Mage 
           option(value="Paladin") Paladin 
           option(value="Priest") Priest 
           option(value="Rogue") Rogue 
           option(value="Shaman") Shaman 
           option(value="Warlock") Warlock 
           option(value="Warrior") Warrior 
        .col-md-6 
         .form-group 
          label(for="filter") Filter by 
          select.form-control(name="filterBy") 
           option(value="0" selected) All guides 
           option(value="most_viewed") Most viewed 
           option(value="top_rated") Top rated 
           option(value="most_commented") Most commented 

     .container-fluid 
      .table-responsive 
       table.table.table-hover 
        thead 
         tr 
          th hero 
          th title 
          th author 
          th updated 
          th dust 
          th 
           span.glyphicon.glyphicon-eye-open 
          th 
           span.glyphicon.glyphicon-heart 
          th 
           span.glyphicon.glyphicon-comment 
        tbody 
         each guides 
          tr 
           td {{hero}} 
           td 
            a(href="/guide/{{formatId _id}}") {{title}} 
           td {{authorUsername}} 
           td {{moFormat modifiedAt 'YYYY-MM-DD'}} 
           td {{dust}} 
           td {{hitCount}} 
           td {{rating}} 
           td {{commentCount}} 

        tbody 
         each getGuides 
          tr 
           td {{hero}} 
           td 
            a(href="/guide/{{formatId _id}}") {{title}} 
           td {{authorUsername}} 
           td {{moFormat modifiedAt 'YYYY-MM-DD'}} 
           td {{dust}} 
           td {{hitCount}} 
           td {{rating}} 
           td {{commentCount}} 

Każda pomoc lub sugestie są wysoko cenione!

Edit: I uaktualniony pakiet search-source do 1.4.2

+0

'Guides = new Mongo.Collection ("przewodniki");' jest zdefiniowane w skrypt po stronie klienta. '' Przewodniki' jest również wywoływany w skrypcie po stronie serwera, ale nie jest dostępny, ponieważ został zdefiniowany w skrypcie klienta. Spróbuj przenieść ten wiersz kodu do pliku js w folderze 'lib', aby był dostępny zarówno na serwerze, jak i na kliencie. Jeśli to nie wszystko, możesz dołączyć kod HTML do swojego szablonu. –

+0

@BrianShamblen Deklaracja kolekcji nie była winna. Ale zredagowałem mój post i opublikowałem mój szablon :) –

+0

Uważam, że jest to spowodowane (nieudokumentowanym) problemem, o którym wspominam w mojej odpowiedzi. Jeśli nie, sprawdź, czy w dzienniku serwera nie ma żadnych błędów. Ten pakiet wymaga trochę miłości i aktualizacji :) – MasterAM

Odpowiedz

3

Uważam, że problemem jest brak options przekazywane do metody GuideSearch.search.

Prowadzi to do tego, że obsługa definicji wyszukiwania otrzymuje null dla opcji.

SearchSource.defineSource('guides', function(searchText, options) { 
    if(searchText) { 
    var regExp = buildRegExp(searchText); 
    var selector = {title: regExp} 
    return Guides.find(selector, options).fetch(); //illegal 
    } else { 
    return Guides.find({}, options).fetch(); 
    } 
}); 

Wynika to w zbiorach za find() metody uzyskiwania NULL options argumenty, że jeśli dostarczone, muszą być obiektu (a nie null).

Dlatego też sprawdzić null options w źródle danych i przekazać pusty obiekt (lub nic) metody find() lub przekazać pusty obiekt metody GuideSearch.search():

Template.guide_list.events({ 
    "keyup #title": _.throttle(function(e) { 
     var text = $(e.target).val().trim(); 
     GuideSearch.search(text, {}); // here 
    }, 200) 
}); 

Powinieneś prawdopodobnie upewnij się, że options nie jest w metodzie serwera tak jak w odpowiedzi @ webdeb.

Dodatkowo, niektóre pakiety (check i ejson) muszą zostać dodane jako zależności do aplikacji, ponieważ pakiet meteorhacks:search-source używa ich bez deklarowania zależności. Jest to spowodowane wprowadzeniem zmian w wersji 1.2.0. (wcześniej symbole te były automatycznie dostępne dla pakietów).

Aby najpierw uzyskać wszystkie dostępne wyniki, można wyzwolić wyszukiwanie po utworzeniu szablonu. Należy zauważyć, że może to być dość kosztowne, gdy masz dużo danych, więc prawdopodobnie powinieneś ograniczyć wyniki zwracane przez program obsługi definicji wyszukiwania na serwerze.

Template.guide_list.onCreated(function() { 
    GuideSearch.search('', {}); 
}); 

Aby wyświetlić tytuł poprawnie w wynikach wyszukiwania, można użyć Spacebars.SafeString() tak, że płomień nie wie, co czyni go jako HTML.

Template.guide_list.helpers({ 
    getGuides: function() { 
     return GuideSearch.getData({ 
      transform: function (matchText, regExp) { 
       return Spacebars.SafeString(matchText.replace(regExp, "<b>$&</b>")) 
      } 
     }); 
    }, 
    formatId: function(id) { 
     return id; 
    }, 
    moFormat: function(date, format) { 
     return moment(date).format(format); 
    }, 
    isLoading: function() { 
     return GuideSearch.getStatus().loading; 
    } 
}); 

Template.guide_list.events({ 
    "keyup #title": _.throttle(function(e) { 
     var text = $(e.target).val().trim(); 
     GuideSearch.search(text, {/* your options here */}); 
    }, 200) 
}); 

lub, alternatywnie, użyć potrójnego notacji nawiasów:

a(href="/guide/{{formatId _id}}") {{{title}}} 

Warning: Należy zdezynfekować swój matchText kiedy to robi.

Publikacje nie powinny mieć nic wspólnego z wynikami, ponieważ pakiet wykorzystuje własną kolekcję.

+1

Jestem zaintrygowany. Mam działającą wersję na mojej maszynie. Jedyne, co musiałem zrobić, to dodać 'check' i' ejson', ponieważ pakiet używa ich bez deklarowania zależności (ponieważ nie są one automatycznie dostępne tak jak przed wersją 1.2) i upewnij się, że argument "options" dostarczone do 'Guides.find()' na serwerze nie było 'null'. – MasterAM

+0

TY jesteś człowiekiem! teraz działa jak charm =)! Wystarczyło dodać pakiet 'check' i' ejson'. Byłoby dobrze, gdybyś dodał to do swojej odpowiedzi wtedy: przy okazji, kiedy renderuję szablon, początkowo nie ma wyników. Właśnie wtedy, gdy szukam pól, pojawiają się. Co robisz, aby wyświetlić wszystkie możliwe wpisy dostępne na początku, zanim użytkownik czegoś przeszuka? –

+1

Miło to słyszeć. Dodałem kilka wyjaśnień, aby zacząć i rozwiązać kilka drobnych problemów, które znalazłem. – MasterAM

1

zgadzam się z odpowiedzią od @MasterAM, ale aby rozwiązać ten problem wystarczy umieścić to w swoim SearchSource funkcję:

SearchSource.defineSource('guides', function(searchText, options) { 
    options = options || {}; // to be sure, that options is at least an empty object 
    if(searchText) { 
    var regExp = buildRegExp(searchText); 
    ... 
Powiązane problemy