PhoneGap, accedere al File System

di: Andrea Stagi     02 Novembre 2011

In questo articolo vedremo come poter interagire con il File System dei dispositivi mobili attraverso PhoneGap. In questo modo possiamo gestire file e cartelle all'interno delle nostre applicazioni.

Chi non conoscesse questo framework può leggere questa introduzione a PhoneGap e colmare il "gap" :).

Progetto: gestire le ricette con PhoneGap

Per approfondire il tema della gestione dei file ci serviamo di un esempio pratico: creeremo un'applicazione per gestire ricette di cucina.

Il nostro software permetterà all'utente di inserire una ricetta, visualizzarla e caricare un file con tutti i dati su un server. Inoltre, per ampliare la conoscenza degli strumenti forniti da PhoneGap, indicizzeremo questi file con un database locale in modo da interrogare il database per vedere tutte le ricette inserite, invece di estrarle dal contenuto di una cartella.

Ecco gli screenshot dell'applicazione:

Figura 1. Il ciclo dell'applicazione
(clic per ingrandire)

Ciclo dell'applicazione

Creare file e cartelle con PhoneGap

Come prima cosa creiamo la cartella che conterrà le ricette. Per creare una cartella sullo smartphone dobbiamo richiamare il metodo:

fs.getDirectory("LeMieRicette", {create: true, exclusive: false}, successSave, fail);

dell'oggetto fs di tipo File System preso con PhoneGap.

Come dicevamo nell'articolo precedente, possiamo associare ad un evento una funzione, in questo caso potremmo gestire l'evento di device_ready con una funzione che ci permetta di agganciarci al File System, creando un apposito oggetto e memorizzandolo in un'area che andremo poi a reperire.

Funzioni di scrittura

Iniziamo dalle funzioni di write dell'applicazione, in modo da poter avere dei dati reali sui quali lavorare in fase di lettura e upload. Vediamo quali sono i passi da compiere:

  1. Creare il nostro menu di partenza e lavorare sul bottone Nuova ricetta
  2. Collegare questo pulsante alla pagina che ci mostrerà un modulo di registrazione dove inserire titolo e testo della ricetta

Vediamo quindi come compierli utilizzando strumenti di PhoneGap.

Aggiungiamo il pulsante con il comando Aggiungi e associamo un'azione che possiamo definire con un piccolo scriptt nell'header del nostro file HTML. Visto che si tratta di una pagina il cui scopo è solo quello di memorizzare una ricetta, possiamo eseguire tutte le azioni in un click e creare una serie di procedure in caso di successo e di fallimento. Iniziamo con l'ottenere l'accesso al file system:

function onClick() {
  window.requestFileSystem(LocalFileSystem.PERSISTENT, 0, gotFS, fail);
}    

Nel parametro gotFS possiamo chiedere di ottenere l'oggetto Directory, crearla se non esiste e, nella callback di successo (directoryFS) aprire il file e creare quindi un oggetto opportuno da passare alla funzione gotFileEntry dove il titolo della ricetta sarà il nome del file:

function gotFS(fileSystem) {
  fileSystem.root.getDirectory("LeMieRicette", {create: true, exclusive: false}, directoryFS, fail);
}

function directoryFS(fileSystem) {
  fileSystem.getFile(document.getElementById('recipe_title').value, {create: true}, gotFileEntry, fail);
}

Una volta creato il file, dobbiamo creare un oggetto di tipo writer che ci permetterà di scrivere i nostri dati:

function gotFileEntry(fileEntry) {
  fileEntry.createWriter(saveRecipe, fail);
}

La funzione principale dell'oggetto writer è la funzione write, alla quale passiamo i conenuti da salvare.

function saveRecipe(writer) {
  writer.write(document.getElementById('recipe_text').value);
}

Possiamo inoltre definire cosa deve succedere una volta invocata write, passando una funzione all'evento onwrite del writer.

Memorizzare dati su SQLite

Nel nostro caso vogliamo indicizzare il file nel database. I database che vengono utilizzati in Android sono di tipo Sqlite. Per aprire un database è necessario ricorrere alla funzione openDatabase, alla quale passeremo il nome del database, la versione, il nome visualizzato e la dimensione in byte:

var db = window.openDatabase("myrecipes", "1.0", "Recipes", 200000);

Per eseguire una qualsiasi operazione applicheremo invece il metodo transaction sull'oggetto appena ottenuto. Il metodo transaction necessita come parametri la funzione dove si esegue l'operazione, la callback di errore e quella di successo, quindi nel nostro caso avremo:

db.transaction(populateDB, errorCB, successCB);

Infine costruiamo la nostra funzione di salvataggio più elaborata:

function saveRecipe(writer) {
  
  writer.onwrite = function(evt) {
    var db = window.openDatabase("myrecipes", "1.0", "Recipes", 200000);
	db.transaction(populateDB, errorCB, successCB);
  };
  
  writer.write(document.getElementById('recipe_text').value);
}

function populateDB(tx) {
  tx.executeSql('CREATE TABLE IF NOT EXISTS Recipes (id INTEGER PRIMARY KEY AUTOINCREMENT, data)');
  tx.executeSql('INSERT INTO Recipes (data) VALUES (\"' + document.getElementById('recipe_title').value + '\")');
}

function errorCB(err) {
  alert("Error processing SQL: " + err.code);
}

function successCB() {
  alert("success!");
}

Le callback di fallimento e successo sono piuttosto esplicative. Adesso possiamo creare qualche ricetta per poi eseguire il testing nella fase di lettura.

Guide JavaScript

Guida Node.js

Il framework che permette di per usare V8, l'interprete JavaScript...

Canvas, guida ai framework

Canvas, tra gli elementi di HTML5 è forse quello di maggior impatto....

Guida jQuery UI

Creare siti ricchi e dinamici con jQuery UI, il progetto ufficiale...

Altre guide

Newsletter @JavaScript

Ogni martedì, direttamente nella tua e-mail: guide, articoli, script, novità e approfondimenti tecnici su JavaScript.

Iscriviti alla newsletter

Altre newsletter

Corsi in aula

Corso Webmaster base

18 Giugno 2012 a Milano
Disponibilità: 6 Posti

Corso Google AdWords Base

25 Giugno 2012 a Milano
Disponibilità: 7 Posti

Corso JQuery e Ajax per Webmaster

03 Luglio 2012 a Milano
Disponibilità: 7 Posti

Corso Google AdWords Base

05 Giugno 2012 a Roma
Disponibilità: 7 Posti

Corso Webmaster base

11 Giugno 2012 a Roma
Disponibilità: 7 Posti