Kako dodati moćnu tražilicu u svoj Rails backback

Fotografija Simona Abramsa na Unsplash

U mom iskustvu kao programer Ruby on Rails, često sam se morao baviti dodavanjem funkcionalnosti pretraživanja web aplikacijama. U stvari, gotovo sve aplikacije na kojima sam u nekom trenutku radio, trebale su mogućnosti tražilice, dok su mnoge od njih imale tražilicu kao najvažniju funkcionalnost jezgre.

Mnoge aplikacije koje svakodnevno koristimo bile bi beskorisne bez dobre tražilice u svojoj osnovi. Na primjer, na Amazonu možete pronaći određeni proizvod među više od 550 milijuna proizvoda koji su dostupni na web mjestu u samo nekoliko sekundi - a sve zahvaljujući pretraživanju punog teksta u kombinaciji s filtrima kategorija, oblicima i sustavom preporuka.

Na Airbnbu možete potražiti stan kombinirajući geoprostornu pretragu s filtrima na karakteristike kuće, poput dimenzije, cijene, raspoloživih datuma i tako dalje.

I Spotify, Netflix, Ebay, Youtube ... svi se u velikoj mjeri oslanjaju na tražilicu.

U ovom ću članku opisati kako razviti API za Ruby on Rails 5 s Elasticsearch-om. Prema DB Engines Rankingu, Elasticsearch je trenutno najpopularnija platforma za pretraživanje otvorenog koda.

Ovaj članak neće ići u detalje Elasticsearcha i kako se uspoređuje sa svojim konkurentima poput Sphinx i Solr. Umjesto toga, to će biti korak po korak vodič o tome kako implementirati JSON API Backup with Ruby on Rails i Elasticsearch, koristeći test Driven Development razvoj.

Ovaj članak obuhvaća:

  1. Elasticsearch Postavljanje za testiranje, razvoj i proizvodna okruženja
  2. Postavljanje testnog okoliša Ruby on Rails
  3. Indeksiranje modela uz pomoć elastičnog pretraživanja
  4. Krajnja točka pretraživanja API-ja

Kao i u mom prethodnom članku, Kako povećati performanse sa arhitekturom bez poslužitelja, ja ću sve opisati korak po korak. Zatim možete sami isprobati i imati jednostavan radni primjer na kojem ćete sagraditi nešto složenije.

Primjer aplikacije bit će pretraživač filma. Imat će jedinstvenu krajnju točku API JSON koja vam omogućuje pretraživanje punog teksta na Naslovima filmova i pregledima filmova.

1. Postavljanje elastične pretrage

Elasticsearch je distribuirani, RESTful mehanizam za pretraživanje i analitiku koji je sposoban riješiti sve veći broj slučajeva korištenja. Kao srce elastičnog snopa, on središnje pohranjuje vaše podatke kako biste mogli otkriti očekivano i otkriti neočekivano. - www.elastic.co/products/elasticsearch

Prema DB-Enginein-ovom rangiranju tražilica, Elasticsearch je daleko najpopularnija platforma za tražilice danas (od travnja 2018.). I to je od kraja 2015., kada je Amazon najavio pokretanje AWS Elasticsearch Service, način za pokretanje klastera Elasticsearch s konzole AWS Management.

Trend rangiranja na tražilicama DB motora

Elasticsearch je open source. Možete preuzeti željenu verziju s njihove web stranice i pokrenuti je gdje god želite. Iako predlažem korištenje AWS Elasticsearch usluge za potrebe proizvodnje, radije bih pokrenuo Elasticsearch na svom lokalnom stroju radi testiranja i razvoja.

Započnimo preuzimanjem (trenutno) najnovije verzije Elasticsearch (6.2.3) i raspakujte je. Otvorite terminal i pokrenite

$ wget https://artifacts.elastic.co/downloads/elasticsearch/elasticsearch-6.2.3.zip
$ unzip elastična pretraga-6.2.3.zip

Ovdje možete preuzeti Elasticsearch iz svog preglednika i raspakirati ga sa svojim preferiranim programom.

2. Testiranje okruženja

Izgradit ćemo sigurnosnu aplikaciju s API-jem Ruby on Rails 5. Imat će jedan model koji predstavlja Filmove. Elasticsearch će to indeksirati, a to će se pretraživati ​​putem krajnje točke API-ja.

Prije svega, napravimo novu aplikaciju za tračnice. U istoj mapi koju ste ranije preuzeli Elasticsearch, pokrenite naredbu za generiranje nove aplikacije tračnica. Ako vam je novo Ruby on Rails, pogledajte ovaj početni vodič kako biste prvo postavili svoje okruženje.

$ rails novi filmovi za pretraživanje --api; pretraga CD-a

Kada koristite opciju "api", nisu uključeni svi srednji softveri koji se primarno koriste za aplikacije preglednika. Točno ono što želimo. Pročitajte više o tome izravno na vodiču s rubinom na tračnicama.

Sada dodajmo sve dragulje koji će nam trebati. Otvorite svoj Gemfile i dodajte sljedeći kôd:

# Gemfile
...
# Elasticsearch integracija
dragulj 'elastični model'
dragulj 'elastične tračnice'
grupa: razvoj,: test do
  ...
  # Okvir ispitivanja
  dragulj 'rspec'
  dragulj 'rspec-tračnice'
kraj
grupa: test do
  ...
  # Čista baza podataka između testova
  gem 'database_cleaner'
  # Programirano pokrenite i zaustavite ES za testove
  dragulj 'elastične ekstenzije'
kraj
...

Dodajemo dva Elasticsearch dragulja koji će pružiti sve potrebne metode za indeksiranje našeg modela i pokretanje upita za pretraživanje na njemu. Za testiranje se koriste rspec, rspec-tračnice, čistač baze podataka i elastične ekstenzije.

Nakon što spremite svoj Gemfile, pokrenite instalaciju paketa kako biste instalirali sve dodane dragulje.

Sada konfiguriramo Rspec pokretanjem sljedeće naredbe:

šine generiraju rspec: instalirati

Ova naredba će stvoriti mapu spec. I dodati spec_helper.rb i rails_helper.rb u nju. Oni se mogu koristiti za prilagodbu rspeca vašim potrebama.

U ovom ćemo slučaju dodati blok DatabaseCleaner rails_helper.rb tako da se svaki test izvodi u praznoj bazi podataka. Nadalje, izmijenit ćemo spec_helper.rb kako bismo pokrenuli testni poslužitelj Elasticsearch svaki put kada se pokrene testni paket i ponovo ga isključili nakon završetka testnog skupa.

Ovo se rješenje temelji na članku Rowana Oultona Ispitivanje elastičnog pretraživanja u tračnicama. Mnogo pljeska za njega!

Počnimo s DatabaseCleaner. Unutar specifikacije / rails_helper.rb dodajte sljedeći kôd:

# spec / rails_helper.rb
...
RSpec.configure do | config |
  ...
config.before (: suite) učiniti
    DatabaseCleaner.strategy =: transakcija
    DatabaseCleaner.clean_with (: odbacivanje)
  kraj
config.around (: svaki) učiniti | primjer |
    Čišćenje baze podataka
      example.run
    kraj
  kraj
kraj

Zatim razmislimo o postavljanju testnog poslužitelja Elasticsearch. Moramo dodati neke konfiguracijske datoteke kako bi Rails znao gdje pronaći izvršnu Elasticsearch. Također će mu reći na kojem portu želimo da se izvodi, na temelju trenutnog okruženja. Da biste to učinili, dodajte novu konfiguracijsku yaml u svoju config folder:

# config / elasticsearch.yml
razvoj: i zadani
  es_bin: '../elasticsearch-6.2.3/bin/elasticsearch'
  host: 'http: // localhost: 9200'
  priključak: '9200'
test:
  es_bin: '../elasticsearch-6.2.3/bin/elasticsearch'
  host: 'http: // localhost: 9250'
  port: '9250'
staging:
  <<: * zadano
proizvodnja:
  es_bin: '../elasticsearch-6.2.3/bin/elasticsearch'
  host: 'http: // localhost: 9400'
  priključak: '9400'

Ako niste kreirali aplikaciju za tračnice u istoj mapi u kojoj ste preuzeli Elasticsearch ili koristite drugu verziju Elasticsearch-a, morat ćete ovdje prilagoditi put es_bin.

Sada dodajte novu datoteku u mapu inicijalizatora koja će se čitati iz konfiguracije koju smo upravo dodali:

# config / inicijalizatori / elasticsearch.rb
ako File.exists? ("config / elasticsearch.yml")
   config = YAML.load_file ("config / elasticsearch.yml") [Rails.env] .symbolize_keys
   Elasticsearch :: Model.client = Elasticsearch :: Client.new (config)
kraj

I na kraju promijenimo spec_helper.rb kako bismo uključili test test Elasticsearch. To znači pokrenuti i zaustaviti Elasticsearch testni poslužitelj i stvoriti / izbrisati Elasticsearch indekse za naš model Rails.

# spec / spec_helper.rb
zahtijevaju 'elastična pretraga / proširenja / test / cluster'
zahtijevaju 'yaml'
RSpec.configure do | config |
  ...
  # Pokrenite grupu u memoriji za Elasticsearch prema potrebi
  es_config = YAML.load_file ("config / elasticsearch.yml") ["test"]
  ES_BIN = es_config ["es_bin"]
  ES_PORT = es_config ["port"]
config.before: all, elastična pretraga: true do
    Elasticsearch :: Proširenja :: Test :: Cluster.start (naredba: ES_BIN, port: ES_PORT.to_i, čvorovi: 1, vrijeme: 120) osim ako Elasticsearch :: Proširenja :: Test :: Cluster.running? (Naredba: ES_BIN, na: ES_PORT.to_i)
  kraj
# Zaustavite elastični skup nakon probnog trčanja
  config.after: suite do
    Elasticsearch :: Proširenja :: Test :: Cluster.stop (naredba: ES_BIN, port: ES_PORT.to_i, čvorovi: 1) ako Elasticsearch :: Proširenja :: Test :: Cluster.running? (Naredba: ES_BIN, u: ES_PORT. to_i)
  kraj
# Stvorite indekse za sve elastične modele za pretraživanje
  config.before: svaki, elastična pretraga: true do
    ActiveRecord :: Base.descendants.each do | model |
      ako je model. reply_to? (: __ elastično traženje__)
        početi
          Model .__ elasticsearch __. create_index!
          Model .__ elasticsearch __. refresh_index!
        spasiti => Elasticsearch :: Transport :: Transport :: Pogreške :: NotFound
          # Ovo ubija "pogreške ne postoji", piše se na konzoli
        spasiti => e
          STDERR.puts "Došlo je do pogreške pri kreiranju indeksa elastičnih pretraživanja za # {model.name}: # {e.inspect}"
        kraj
      kraj
    kraj
  kraj
# Izbrišite indekse za sve elastične modele za pretraživanje kako biste osigurali čisto stanje između testova
  config.after: svaki, elastična pretraga: true do
    ActiveRecord :: Base.descendants.each do | model |
      ako je model. reply_to? (: __ elastično traženje__)
        početi
          Model .__ elasticsearch __. delete_index!
        spasiti => Elasticsearch :: Transport :: Transport :: Pogreške :: NotFound
          # Ovo ubija "pogreške ne postoji", piše se na konzoli
        spasiti => e
          STDERR.puts "Došlo je do pogreške prilikom uklanjanja indeksa elastičnog pretraživanja za # {model.name}: # {e.inspect}"
        kraj
      kraj
    kraj
  kraj
kraj

Definirali smo četiri bloka:

  1. prije (: all) blok koji pokreće testni poslužitelj Elasticsearch, osim ako se već pokreće
  2. blok after (: suite) koji zaustavlja testni poslužitelj Elasticsearch, ako se pokreće
  3. prije (: svaki) blok koji stvara novi indeks Elasticsearch za svaki model koji je konfiguriran s Elasticsearch
  4. blok nakon (: svaki) koji briše sve indekse Elasticsearch

Dodavanje elastičnog pretraživanja: true osigurava da će se ovi testovi pokretati samo testovi označeni elastičnim pretraživanjem.

Otkrivam da ovo postavljanje izvrsno funkcionira kada jednom pokrenete sve svoje testove, primjerice prije implementacije. S druge strane, ako koristite razvojno prilagođeni test i pokrećete svoje testove vrlo često, vjerojatno ćete trebati malo izmijeniti ovu konfiguraciju. Ne želite pokrenuti i zaustaviti testni poslužitelj Elasticsearch pri svakoj probnoj vožnji.

U tom slučaju možete komentirati blok nakon (: suite) na mjestu gdje je testni poslužitelj zaustavljen. Možete ga isključiti ručno ili upotrebom skripte, kad vam više ne treba.

zahtijevaju 'elastična pretraga / proširenja / test / cluster'
es_config = YAML.load_file ("config / elasticsearch.yml") ["test"]
ES_BIN = es_config ["es_bin"]
ES_PORT = es_config ["port"]
Elasticsearch :: Proširenja :: Test :: Cluster.stop (naredba: ES_BIN, port: ES_PORT.to_i, čvorovi: 1)

3. Indeksiranje modela pomoću Elasticsearch-a

Sada počinjemo implementirati naš Model filma s mogućnostima pretraživanja. Koristimo test vođen razvojnim pristupom. To znači da prvo pišemo testove, vidimo ih kako propadaju, a zatim pišemo kod da bi prošli.

Prvo moramo dodati model filma koji ima četiri atributa: naslov (String), pregled (Text), image_url (String) i prosječna vrijednost glasova (Float).

$ rails g model Naslov filma: string string pregled: text image_url: string voice_average: float
$ rails db: migrirati

Sada je vrijeme za dodavanje Elasticsearch-a u naš model. Napisimo test koji provjerava je li naš model indeksiran.

# spec / models / movie_spec.rb
zahtijevaju 'rails_helper'
RSpec.prikažite film, elastična pretraga: true,: type =>: model do
  to 'treba indeksirati' učiniti
     očekujte (Movie .__ elastično traženje __. indeks_eksistira?) .na beutruthy
  kraj
kraj

Ovaj test će provjeriti je li kreiran indeks elastičnog pretraživanja za Film. Imajte na umu da prije početka testiranja automatski kreiramo indeks elastičnog pretraživanja za sve modele koji odgovaraju metodi __elasticsearch__. To znači za sve modele koji uključuju module za elastično traženje.

Pokrenite test da provjerite da nije uspio.

bundle exec rspec specifikacije / modeli / movie_spec.rb

Kad prvi put pokrenete ovaj test, trebali biste vidjeti kako pokreće testni poslužitelj Elasticsearch. Test ne uspijeva jer nismo dodali nijedan modul Elasticsearch u naš model filma. Riješimo to sada. Otvorite model i dodajte sljedeće Elasticsearch da biste uključili:

# app / modeli / movie.rb
klasni film 

To će dodati neke metode Elasticsearch našem modelu filma, poput nedostajuće metode __elasticsearch__ (koja je stvorila grešku u prethodnom ispitnom ciklusu) i metode pretraživanja koju ćemo koristiti kasnije.

Ponovite test i pogledajte da je prošao.

bundle exec rspec specifikacije / modeli / movie_spec.rb

Sjajno. Imamo indeksirani filmski model.

Prema zadanim postavkama, Elasticsearch :: Model postavit će indeks sa svim atributima modela, automatski zaključujući njihove vrste. Obično to nije ono što želimo. Sada ćemo prilagoditi indeks modela tako da ima sljedeće ponašanje:

  1. Samo se naslov i pregled trebaju indeksirati
  2. Treba koristiti stenming (što znači da bi pretraživanje "glumaca" trebalo vratiti i filmove koji sadrže tekst "glumac" i obrnuto)

Također želimo da se naš indeks ažurira svaki put kada se film doda, ažurira ili izbriše.

Prevedimo to u testove dodavanjem sljedećeg koda u movie_spec.rb

# spec / models / movie_spec.rb
RSpec.prikažite film, elastična pretraga: true,: type =>: model do
  ...
opišite "#search" učiniti
    prije (: svaki) učiniti
      Movie.create (
        naslov: "Rimski odmor",
        pregled: "Američki romantični komedija iz 1953. ...",
        image_url: "wikimedia.com/Roman_holiday.jpg",
        prosjek glasova: 4,0
      )
      Film .__ elasticsearch __. Refresh_index!
    kraj
    to "bi trebao indeksirati naslov" učiniti
      očekujte (Movie.search ("Odmor"). records.length) .to eq (1)
    kraj
    to "treba indeksirati pregled" učiniti
      očekivati ​​(Movie.search ("komedija"). records.length) .to eq (1)
    kraj
    to "ne bi trebalo indeksirati image_path" učiniti
      očekujte (Movie.search ("Roman_holiday.jpg"). records.length) .to eq (0)
    kraj
    to "ne bi trebalo indeksirati voice_average" učiniti
      očekujte (Movie.search ("4.0"). records.length) .to eq (0)
    kraj
  kraj
kraj

Film stvaramo prije svakog testa jer smo konfigurirali DatabaseCleaner tako da je svaki test izoliran. Film .__ elasticsearch __. Refresh_index! treba biti siguran da je novi filmski zapis odmah dostupan za pretraživanje.

Kao i prije, pokrenite test i uvjerite se da nije uspio.

Čini se da se naš film ne indeksira. To je zato što još nismo rekli modelu što treba raditi kad se podaci filma promijene. Srećom, to se može popraviti dodavanjem još jednog modula u naš filmski model:

klasni film 

S Elasticsearch :: Model :: Povratni pozivi, svaki put kada se film doda, promijeni ili izbriše, ažurira se i njegov dokument o Elasticsearch.

Pogledajmo kako se mijenja izlazni test.

U redu. Sada je problem što naša metoda pretraživanja također vraća upite koji se podudaraju s atributima voice_average i image_url. Da bismo riješili to moramo konfigurirati mapiranje indeksa Elasticsearch. Stoga moramo Elasticsearchu konkretno reći koji model pripisuje indeksu.

# app / modeli / movie.rb
klasni film 
# Indeks elastičnog pretraživanja
  indeks postavki: {number_of_shards: 1} učiniti
    mapiranje dinamično: 'lažno' napraviti
      indeksi: naslov
      indeksi: pregled
    kraj
  kraj
kraj

Ponovite test i pogledajte da je prošao.

Cool. Sada dodajmo štrudlu kako ne bi bilo razlike između "glumac" i "glumci". Kao i uvijek, prvo ćemo napisati test i vidjeti kako nije uspio.

opišite "#search" učiniti
    prije (: svaki) učiniti
      Movie.create (
        naslov: "Rimski odmor",
        pregled: "Američki romantični komedija iz 1953. ...",
        image_url: "wikimedia.com/Roman_holiday.jpg",
        prosjek glasova: 4,0
      )
      Film .__ elasticsearch __. Refresh_index!
    kraj
...
to bi "trebalo primijeniti na naslovu" učiniti
      očekivati ​​(Movie.search ("Praznici"). records.length) .to eq (1)
    kraj
to "treba primijeniti na osnovu pregleda" učiniti
      očekivati ​​(Movie.search ("film"). records.length) .to eq (1)
    kraj
kraj

Imajte na umu da testiramo oba načina: Praznici bi trebali vratiti i Praznik, a Film također treba vratiti Filmove.

Da bi ovi testovi ponovo prošli, moramo izmijeniti mapiranje indeksa. Ovog puta to ćemo učiniti dodavanjem engleskog analizatora u oba polja:

klasni film 
# Indeks elastičnog pretraživanja
  indeks postavki: {number_of_shards: 1} učiniti
    mapiranje dinamično: 'lažno' napraviti
      indeksi: naslov, analizator: 'engleski'
      indeksi: pregled, analizator: 'engleski'
    kraj
  kraj
kraj

Ponovno pokrenite svoje testove da biste vidjeli kako prolaze.

Elasticsearch je vrlo moćna platforma za pretraživanje i mogli bismo dodati puno funkcionalnosti našoj metodi pretraživanja. Ali to nije u dosegu ovog članka. Ovdje ćemo se zaustaviti i prijeći na izgradnju dijela kontrolera JSON API-ja putem kojeg se pristupa metodi pretraživanja.

4. Krajnja točka API pretraživanja

API pretraživanja koji gradimo trebao bi korisnicima omogućiti pretraživanje cijelog teksta na Tablici filmova. Naš API ima jednu krajnju točku definiranu na sljedeći način:

uRL:
 GET / api / v1 / filmovi
parametri:
 * q = [string] je potreban
Primjer URL-a:
 GET / api / v1 / movies? Q = Romi
Primjer odgovora:
[{ "_Index": "filmovi", "_ tip": "Film", "_ id": "95088", "_ rezultat": 11,549209, "_ izvor": { "id": 95088 "title": "Roma" , "pregled": "Gotovo besmislen, nagonski, impresionistički portret Rima kroz oči jednog od njegovih najpoznatijih građana.", "image_url": "https://image.tmdb.org/t/p/w300/ rqK75R3tTz2iWU0AQ6tLz3KMOU1.jpg”, "vote_average": 6.6 "created_at": "2018-04-14T10: 30: 49.110Z", "updated_at": "2018-04-14T10: 30: 49.110Z"}}, ... ]

Ovdje definiramo našu krajnju točku prema nekim najboljim praksama RESTful API Design:

  1. URL treba kodirati objekt ili resurs, dok bi radnju koju treba poduzeti kodirali HTTP metodom. U ovom slučaju, resurs su filmovi (zbirka), a mi koristimo HTTP metodu GET (jer tražimo podatke iz resursa bez stvaranja bilo kakvih nuspojava). Parametre URL-a koristimo za daljnje definiranje načina na koji bi se ovi podaci trebali dobiti. U ovom primjeru, q = [string], koji određuje upit za pretraživanje. Više o tome kako dizajnirati RESTful API-je možete pročitati u članku Maheša Haldara Smjernice za dizajniranje API-ja RESTful - Najbolje prakse.
  2. Također dodajemo verziju našeg API-ja dodavanjem v1 našem URL-u krajnje točke. Verzija vašeg API-ja vrlo je važna, jer vam omogućuje uvođenje novih značajki koje nisu kompatibilne s prethodnim izdanjima bez probijanja svih klijenata koji su razvijeni za prethodne verzije vašeg API-ja.

U redu. Krenimo s implementacijom.

Kao i uvijek, započinjemo s neuspjelim testovima. Unutar specifikacije mape stvorit ćemo strukturu mape koja odražava našu strukturu URL-a krajnje točke API-ja. To znači kontroleri → api → v1 → movies_spec.rb

To možete učiniti ručno ili s vašeg terminala:

mkdir -p specifikacije / kontroleri / api / v1 &&
dodirni specifikacije / kontroleri / api / v1 / movies_spec.rb

Testovi o kojima ćemo ovdje pisati su testovi kontrolera. Ne trebaju provjeravati logiku pretraživanja definiranu u modelu. Umjesto toga, testirat ćemo tri stvari:

  1. GET zahtjev za / api / v1 / movies? Q = [string] nazvat će Movie.search sa [string] kao parametrom
  2. Izlaz Movie.search vraća se u JSON formatu
  3. Vraća se status uspjeha
Ispitivanje kontrolera treba testirati ponašanje regulatora. Ispitivanje kontrolera ne smije propasti zbog problema u modelu.
(Recept 20 - recept za test šina 4. Noel Rappin)

Pretvorimo to u kod. Unutar specifikacije / kontroleri / api / v1 / movies_spec.rb dodajte sljedeći kôd:

# spec / kontroleri / api / v1 / movies_spec.rb
zahtijevaju 'rails_helper'
RSpec.pripisati Api :: V1 :: MoviesController, upišite:: zahtjev učiniti
  # Potražite film s tekstualnim naslovom filma
  opisati "GET / api / v1 / movies? q =" učiniti
    neka (: naslov) {"film-title"}
    neka (: url) {"/ api / v1 / movies? q = # {naslov}"}
to "poziva Movie.search s ispravnim parametrima" učiniti
      očekujem (Film). primiti (: pretraživanje). s (naslov)
      dobiti URL
    kraj
to "vraća izlaz Movie.search-a" učiniti
      dopustiti (Movie). za primanje (: pretraživanje). i_return ({})
      dobiti URL
      ocekujem (odgovor.body) .to eq ({}. to_json)
    kraj
to 'vraća status uspjeha'
      dopustiti (Film). za primanje (: pretraživanje). s (naslov)
      dobiti URL
      ocekivati ​​(odgovor) .to biti_uspjesan
    kraj
  kraj
kraj

Test će odmah uspjeti jer Api :: V1 :: MoviesController nije definiran, pa prvo to učinimo. Napravite strukturu mape kao i prije i dodajte kontroler filmova.

mkdir -p app / kontroleri / api / v1 &&
dodirni app / kontroleri / api / v1 / movies_controller.rb

Sada dodajte sljedeći kôd aplikaciji / kontroleri / api / v1 / movies_controller.rb:

# app / kontroleri / api / v1 / movies_controller.rb
modul Api
  modul V1
    klasa MoviesController 

Vrijeme je da pokrenemo test i vidimo da nije uspio.

Svi testovi nisu uspjeli jer još uvijek moramo dodati rutu za krajnju točku. Unutar config / route.rb dodajte sljedeći kôd:

# config / route.rb
Rails.application.routes.draw do
  imenski prostor: api do
    prostor s imenima: v1 učiniti
      resursi: filmovi, samo: [: indeks]
    kraj
  kraj
kraj

Ponovno pokrenite testove i pogledajte što se događa.

Prva pogreška govori o tome da moramo dodati poziv na Movie.search unutar našeg kontrolera. Druga se žali na odgovor. Dodajmo nedostajući kod kino-kontrolera:

# app / kontroleri / api / v1 / movies_controller.rb
modul Api
  modul V1
    klasa MoviesController 

Pokrenite test i provjerite jesmo li gotovi.

Yup. To je sve. Završili smo stvarno osnovnu aplikaciju koja omogućava korisnicima da pretražuju model putem API-ja.

Kompletan kod na mom GitHub repo-u možete pronaći ovdje. Možete popuniti svoju tablicu filma nekim podacima pokretanjem tračnica db: seed tako da možete vidjeti aplikaciju u akciji. Ovo će uvesti oko 45k filmova s ​​skupa podataka preuzetih s Kagglea. Pogledajte Readme za više detalja.

Ako vam se svidio ovaj članak, preporučite ga tako što ćete pritisnuti ikonu clap koja ćete naći na dnu ove stranice kako bi ga više ljudi moglo vidjeti na snimku Medium.