Condivisione dei dati con i gesti configurazione di Rails & Heroku

Nella parte I di questa serie, avete visto come abbiamo realizzato una semplice app mobile nel framework Corona che risponde a un'azione simile a un "bump" (chiamata "thump") per inviare un messaggio a un altro dispositivo mobile. La comunicazione tra i due dispositivi mobili avviene tra un processo di server intermedio che corrisponde a due dispositivi "thumped" in base a timestamp e distanza. In questo tutorial, configureremo il processo del server intermedio con Ruby on Rails.

Iniziamo creando il nostro progetto. Poiché utilizzeremo il plugin geokit per aiutare con i nostri calcoli geospaziali, dobbiamo creare questo progetto in Rails 2.3.5 poiché il plugin non è compatibile con 3.0.

Dopo aver effettuato l'accesso al tuo server / account di hosting (nel nostro caso utilizziamo Heroku), digita quanto segue:

 mkdir thump-server cd thump-server / rails. rimuovere public / index.html

Le dichiarazioni sopra creeranno una directory e inizieranno un nuovo progetto di rotaie all'interno di esso. Se hai 3.0 installato sul tuo computer di sviluppo, potresti aver bisogno di installare RVM e creare un gemset separato per questo progetto. Tuttavia, fare questo è al di fuori dello scopo del tutorial. Ora installiamo il plugin geokit.

 script / plugin installa git: //github.com/andre/geokit-rails.git

Una volta completato, è necessario aggiungere la gemma al progetto all'interno di Rails :: Initializer.run do | config | blocco del nostro file environment.rb:

 config.gem "geokit"

Ora che questo plugin è stato aggiunto al progetto, dobbiamo eseguire un comando rake per assicurarci che tutte le gemme richieste siano installate nel nostro sistema.

 rake gems: installa

Geokit si affida al database per eseguire calcoli di distanza piuttosto sofisticati. Per questo motivo, il database SQLite predefinito a cui viene fornito un progetto rails non funzionerà. Geokit richiede che usiamo mysql o postgres db per archiviare i nostri dati. Anche se heroku usa postgres di default, è più comune per le macchine di sviluppo avere mysql installato. La bellezza dell'utilizzo di Rails e ActiveRecord è che non importa. Possiamo sviluppare la nostra app con MySQL e funzionerà perfettamente con Postgres.

 mysql -u root crea database thumpserver;

Ora aggiorneremo il nostro file database.yml in modo che punti al nostro database di sviluppo appena creato "thumpserver".

 sviluppo: adattatore: database mysql: utente thumpserver: root socket: /tmp/mysql.sock pool: 5 timeout: 5000

Finalmente il nostro processo di creazione del progetto è completo. Possiamo iniziare a codificare la logica all'interno del nostro server.

Rails ha un semplice metodo di generazione che crea una risorsa basata su REST per i dati CRUD. Se l'ultima frase non ha alcun senso, ti suggerisco di google "rails restful resources" per saperne di più. Essenzialmente con un comando possiamo creare una tabella di database, un modello, un controller e percorsi all'interno del progetto.

 ./ script / genera risorse thump deviceid: string lat: decimal lng: messaggio decimale: stringa ricevuta: boolean

La nostra risorsa è chiamata thump, quindi generandola in questo modo sarà disponibile all'url / thump una volta che il nostro server è in esecuzione. Abbiamo specificato 5 campi da creare per la nostra tabella di database:

deviceid: l'UID del dispositivo mobile
lat: latitude fornita dal servizio di localizzazione
lng: longitudine
messaggio: il messaggio che verrà trasmesso agli utenti che hanno colpito
ricevuto: questo è un valore booleano da contrassegnare una volta ricevuto un messaggio in modo che non possa essere inviato di nuovo

Rails creerà "automagicamente" campi di timestamp chiamati created_at e updated_at. Utilizzeremo created_at più avanti nel nostro esempio.

Quando abbiamo generato la nostra risorsa, è stato creato un file di migrazione del database dei binari nella cartella "db" del progetto. Il nome del file dovrebbe essere simile a questo: TIMESTAMP_create_thumps.rb

Dobbiamo modificare questo file per garantire che la nostra posizione possa essere archiviata con un numero di cifre decimali sufficiente. Per fare questo semplicemente sostituire queste due linee:

 t.decimal: lat t.decimal: lng

Con le seguenti linee:

 t.decimal: lat,: precision => 8,: scale => 8 t.decimal: lng,: precision => 8,: scale => 8

Ciò garantirà che i nostri campi di latitudine e longitudine possano contenere al massimo 8 posizioni decimali.

Inoltre, per evitare che il campo "ricevuto" nel nostro database sia NULL, dobbiamo aggiungere un'impostazione in modo che il suo valore sia falso per impostazione predefinita. Ancora una volta possiamo fare questo sostituendo questa linea:

 t.boolean: ricevuto

Con questa linea:

 t.boolean: received,: default => false

Ora che la nostra migrazione è impostata, possiamo eseguire il comando rake che creerà effettivamente la tabella all'interno del database:

 rake db: migrate

Per prendere input per i nostri dati, useremo l'azione "crea" nel nostro controller di Thump. Oltre a questo, abbiamo bisogno di un'azione di "ricerca" che richiederà alcuni parametri e cercherà nel database in modo che corrisponda ai due dispositivi thumped. Dobbiamo modificare i nostri route.rb nella directory di configurazione per rispondere all'URL / thump / search su una richiesta GET. Possiamo farlo sostituendo questa linea:

 map.resources: thump

Con questa linea

 map.resources: thumps,: collection => : search =>: get

Successivamente, aggiungiamo le seguenti righe al nostro file thump.rb all'interno di app / modelli.

 act_as_mappable validates_presence_of: lat,: lng,: deviceid

La prima linea rende il nostro modello "mappabile". Questo ci dà alcuni metodi di query extra per aiutare a calcolare la distanza tra due serie di coordinate. La riga successiva aggiunge alcune semplici convalide al nostro modello di dati di Thump per garantire che quando riceviamo un messaggio di thump contenga i campi corretti.

Infine, possiamo creare le nostre azioni per la creazione e la ricerca dei dati nel nostro controller. Grazie alla bellezza e alla semplicità di ActiveRecord, la nostra azione "crea" è piuttosto semplice:

 def crea Thump.create! (params [: thump]) render (: json => : success => true) rescue render (: json => : success => false) end

Nel caso in cui le nostre convalide falliscano, restituiremo un oggetto json con: success => false. Nella parte III del tutorial, espanderemo la nostra app mobile per tener conto di ciò.

La nostra "azione" di ricerca è leggermente più complessa in quanto utilizza alcuni degli helper di query di geokit:

 def search thump = Thump.find (: first,: origin => [parametri [: thump] [: lat], parametri [: thump] [: lng]],: condizioni => ["deviceid! =? AND received = ? ", params [: thump] [: deviceid], false],: order => 'distance asc, created_at desc') raise unless (thump) thump.update_attribute (: received, true) render (: json => : success => true,: message => thump.message) rendering di salvataggio (: json => : success => false) end

Rompiamo questo:

 thump = Thump.find (: first,: origin => [params [: thump] [: lat], params [: thump] [: lng]],: condizioni => ["deviceid! =? AND received =?" , params [: thump] [: deviceid], false],: order => 'distance asc, created_at desc')

In sostanza, stiamo interrogando per la nostra corrispondenza "thump" nel database. Un dispositivo invierà lungo la propria latitudine e longitudine che sarà il nostro punto di origine. Le nostre condizioni assicurano che non troviamo per caso il nostro dispositivo escludendo il nostro deviceid dal set di risultati. Vogliamo anche cercare i punti in cui il campo "ricevuto" è falso. Per trovare la corrispondenza più vicina in entrambe le distanze e il tempo, ordineremo i nostri risultati per distanza tra i 2 punti in ordine crescente (cioè più vicino) e il tempo creato o creato_at in ordine decrescente per trovare il più recente. Evidentemente è improbabile che ci siano dei "thump" contrastanti per la nostra app di test, ma questo tipo di query potrebbe contenere un'applicazione multiutente se lo volessimo.

 raise a meno che thump.update_attribute (: received, true) render (: json => : success => true,: message => thump.message)

Il comando raise rilancerà la nostra progressione di codice nel blocco di salvataggio che restituirà: success => false se non riusciamo a trovare un thump corrispondente. Ciò garantirà che la nostra app mobile riceva almeno qualcosa in caso di errore. Se l'oggetto esiste, imposteremo il campo "ricevuto" su true per garantire che questo messaggio non venga abbinato in una successiva richiesta di dati. La nostra dichiarazione render restituirà un oggetto JSON che il dispositivo che riceve il "thump" interpreterà.

Per testare questo, possiamo eseguire un comando nella console di Rails per creare un record di esempio con un punto di origine di New York:

 Thump.create (: deviceid => "B",: lat => 40.7141667,: lng => - 74.0063889,: message => "B")

Per ottenere una corrispondenza "di tipo" o un risultato positivo, possiamo prima avviare il nostro server sulla porta predefinita 3000:

 ./ Script / server

E poi premi il seguente URL:

http: // localhost: 3000 / tonfi / ricerca tonfo [deviceid] = A & tonfo [lat] = 40,7,141667 millions & tonfo [lng] = -74,0063889

Se tutto va bene, il browser dovrebbe mostrare quanto segue:

  "Messaggio": "B", "successo": true

Questo simula un dispositivo chiamato "A" che riceve un messaggio "thump" dal dispositivo B. E ce l'abbiamo!

La prossima volta?

Rimaniamo sintonizzati per la parte III di questa serie, in cui invieremo l'app del server a Heroku e aggiorneremo la nostra app mobile per comunicare con il server.