Come caricare un file (HTML)
[ Questo articolo è rivolto agli sviluppatori per Windows 8.x e Windows Phone 8.x che realizzano app di Windows Runtime. Gli sviluppatori che usano Windows 10 possono vedere Documentazione aggiornata ]
Questo argomento illustra come caricare dati o file su Internet da un dispositivo.
Le app possono avvalersi delle API illustrate in questo argomento per rendere possibile l'interazione con servizi Web che consentono di usare o condividere diffusi formati multimediali per foto, musica e video.
Per trasferimenti di file di grandi dimensioni, basati su flussi o a più parti (video, musica e immagini grandi), con una durata operativa che può estendersi oltre più sospensioni dell'app e/o cambiamenti nella disponibilità di rete, l'app può usare Background Transfer.
Per un'analisi più dettagliata di Trasferimento in background, vedi Trasferimento di dati in background.
Prerequisiti
Se hai bisogno di aiuto per creare un'app di Windows Store in JavaScript, vedi Creare la prima app di Windows Runtime in JavaScript. Inoltre, in questo argomento si usano promesse JavaScript per completare operazioni asincrone. Per altre informazioni su questo modello di programmazione, vedi Programmazione asincrona in JavaScript con promesse.
Per predisporre la tua app per l'uso in rete, devi impostare la funzionalità nel file Package.appxmanifest del progetto. Per una definizione delle singole funzionalità di rete, vedi Come configurare le funzionalità di isolamento della rete.
Gli esempi della funzionalità Trasferimento in background seguenti si basano su JavaScript e sull'esempio di trasferimento in background.
Operazioni di caricamento con Trasferimento in background
Quando si usa Trasferimento in background, esiste un caricamento in forma di UploadOperation che espone un certo numero di metodi di controllo usati per riavviare o annullare l'operazione. Gli eventi dell'app (come la sospensione o la chiusura) e le modifiche alla connettività vengono gestiti automaticamente dal sistema per ogni UploadOperation. I caricamenti continueranno durante i periodi di sospensione dell'app oppure verranno sospesi e saranno persistenti oltre la chiusura dell'app. L'impostazione della proprietà CostPolicy, inoltre, indicherà se l'app tenterà o meno di avviare caricamenti quando per la connettività Internet si usa una rete a consumo.
Negli esempi seguenti viene illustrato come creare e inizializzare un caricamento di base e come enumerare e reintrodurre le operazioni rese persistenti da una sessione precedente dell'app.
Caricamento di un file
La creazione di un caricamento comincia con BackgroundUploader. Con questa classe si possono specificare i metodi che consentono all'app di configurare il caricamento prima di creare l'oggetto UploadOperation risultante. L'esempio seguente mostra come ottenere questo risultato con gli oggetti Uri e StorageFile richiesti.
Identificare il file e la destinazione per il caricamento
Prima di poter cominciare con la creazione di un oggetto UploadOperation, dobbiamo innanzitutto identificare l'URL della posizione di destinazione del caricamento e il file che verrà caricato. Nell'esempio seguente il valore uriString viene popolato con una stringa dall'input dell'interfaccia utente e il valore file con l'oggetto StorageFile restituito da un'operazione PickSingleFileAsync.
function uploadFile() { var filePicker = new Windows.Storage.Pickers.FileOpenPicker(); filePicker.fileTypeFilter.replaceAll(["*"]); filePicker.pickSingleFileAsync().then(function (file) { if (!file) { printLog("No file selected"); return; } var upload = new UploadOp(); var uriString = document.getElementById("serverAddressField").value; upload.start(uriString, file); // Store the upload operation in the uploadOps array. uploadOperations.push(upload); }); }
Creare e inizializzare l'operazione di caricamento
Nel passaggio precedente, i valori uriString e file sono passati a un'istanza del nostro prossimo esempio, UploadOp, nel quale vengono usati per configurare e avviare la nuova operazione di caricamento. Prima di tutto, il valore uriString viene analizzato per creare l'oggetto Uri necessario.
Le proprietà dell'oggetto StorageFile fornito (file) vengono poi usate da BackgroundUploader per popolare l'intestazione della richiesta e impostare la proprietà SourceFile con l'oggetto StorageFile. Viene quindi chiamato il metodo SetRequestHeader per inserire le informazioni sul nome del file in formato stringa e la proprietà StorageFile.Name.
Infine, BackgroundUploader crea UploadOperation (upload).
function UploadOp() { var upload = null; var promise = null; this.start = function (uriString, file) { try { var uri = new Windows.Foundation.Uri(uriString); var uploader = new Windows.Networking.BackgroundTransfer.BackgroundUploader(); // Set a header, so the server can save the file (this is specific to the sample server). uploader.setRequestHeader("Filename", file.name); // Create a new upload operation. upload = uploader.createUpload(uri, file); // Start the upload and persist the promise to be able to cancel the upload. promise = upload.startAsync().then(complete, error, progress); } catch (err) { displayError(err); } }; // On application activation, reassign callbacks for a upload // operation persisted from previous application state. this.load = function (loadedUpload) { try { upload = loadedUpload; promise = upload.attachAsync().then(complete, error, progress); } catch (err) { displayError(err); } }; }
Nota le chiamate di metodo asincrone definite con le promesse JavaScript. Osservando una riga dell'esempio precedente:
promise = upload.startAsync().then(complete, error, progress);
La chiamata di metodo asincrona è seguita da un'istruzione then che indica i metodi, definiti dall'app, chiamati quando viene restituito un risultato della chiamata di metodo asincrona. Per altre informazioni su questo modello di programmazione, vedi Programmazione asincrona in JavaScript con promesse.
Caricamento di più file
Identificare i file e la destinazione per il caricamento
In uno scenario relativo al trasferimento di più file con un'unica UploadOperation, il processo ha inizio come di solito, con le informazioni sul file locale e l'URI di destinazione richiesto. Analogamente all'esempio precedente, l'URI viene fornito dall'utente finale sotto forma di stringa ed è possibile usare FileOpenPicker per indicare i file anche attraverso l'interfaccia utente. In questo scenario, invece, l'app dovrebbe chiamare il metodo PickMultipleFilesAsync per consentire la selezione di più file attraverso l'interfaccia utente.
function uploadFiles() { var filePicker = new Windows.Storage.Pickers.FileOpenPicker(); filePicker.fileTypeFilter.replaceAll(["*"]); filePicker.pickMultipleFilesAsync().then(function (files) { if (files === 0) { printLog("No file selected"); return; } var upload = new UploadOperation(); var uriString = document.getElementById("serverAddressField").value; upload.startMultipart(uriString, files); // Persist the upload operation in the global array. uploadOperations.push(upload); }); }
Creare oggetti per i parametri forniti
Nei due esempi che seguono il codice usato è contenuto in un solo metodo di esempio, startMultipart, chiamato alla fine del primo passaggio. Ai fini dell'istruzione, il codice del metodo che crea una matrice di oggetti BackgroundTransferContentPart è stato separato dal codice che crea l'UploadOperation risultante.
In primo luogo, la stringa dell'URI fornita dall'utente viene inizializzata come Uri. In secondo luogo, viene eseguita una ripetizione della matrice di oggetti IStorageFile (files) passata a questo metodo, i singoli oggetti vengono usati per creare un nuovo oggetto BackgroundTransferContentPart che viene poi posizionato nella matrice contentParts.
upload.startMultipart = function (uriString, files) { try { var uri = new Windows.Foundation.Uri(uriString); var uploader = new Windows.Networking.BackgroundTransfer.BackgroundUploader(); var contentParts = []; files.forEach(function (file, index) { var part = new Windows.Networking.BackgroundTransfer.BackgroundTransferContentPart("File" + index, file.name); part.setFile(file); contentParts.push(part); });
Creare e inizializzare l'operazione di caricamento in più parti
Una volta popolata la matrice contentParts con tutti gli oggetti BackgroundTransferContentPart che rappresentano i singoli IStorageFile da caricare, siamo pronti a chiamare CreateUploadAsync usando l'Uri per indicare se la richiesta verrà inviata.
// Create a new upload operation. uploader.createUploadAsync(uri, contentParts).then(function (uploadOperation) { // Start the upload and persist the promise to be able to cancel the upload. upload = uploadOperation; promise = uploadOperation.startAsync().then(complete, error, progress); }); } catch (err) { displayError(err); } };
Enumerare le operazioni rese persistenti all'avvio
Durante il completamento o l'annullamento di un UploadOperation vengono rilasciate tutte le eventuali risorse di sistema associate. Tuttavia, se l'app viene terminata prima che si verifichi una di queste situazioni, eventuali operazioni attive vengono sospese e le risorse associate a ognuna di esse viene mantenuta. Se le operazioni non sono enumerate e reintrodotte nella sessione successiva dell'app, non verranno completate e continueranno a occupare risorse del dispositivo.
Prima di definire la funzione che enumera le operazioni persistenti, dobbiamo creare una matrice che conterrà gli oggetti UploadOperation restituiti:
var uploadOperations = [];
Definiamo poi la funzione che enumera le operazioni persistenti e le archivia nella nostra matrice. Nota che il metodo load chiamato per riassegnare i callback a UploadOperation nel caso debba essere persistente oltre la chiusura dell'app, è nella classe UploadOp che definiamo più avanti in questa sezione.
function Windows.Networking.BackgroundTransfer.BackgroundUploader.getCurrentUploadsAsync() { .then(function (uploads) { for (var i = 0; i < uploads.size; i++) { var upload = new UploadOp(); upload.load(uploads[i]); uploadOperations.push(upload); } } };
Nota
Per le app di Windows Phone Store, i trasferimenti in background continuano anche quando l'app non è in primo piano. Poiché l'app non è in esecuzione in questo scenario, non riceverà una notifica al termine del trasferimento. Quando riprendi l'app, se controlli lo stato di un trasferimento completato noterai che è BackgroundTransferStatus.Running. In ogni caso, se associ il trasferimento come nel codice di esempio precedente, il gestore di completamento dell'attività verrà attivato e lo stato del trasferimento verrà aggiornato.
Timeout della richiesta
Ci sono due principali scenari di timeout della connessione da prendere in considerazione.
Quando si stabilisce una nuova connessione per un trasferimento, se la richiesta di connessione non viene stabilita entro cinque minuti viene interrotta.
Dopo che la connessione è stata stabilita, verrà interrotto qualsiasi messaggio di richiesta HTTP che non abbia ricevuto risposta entro due minuti.
Nota In entrambi gli scenari, e posto che la connettività Internet esista, la funzionalità Trasferimento in background effettuerà altri tre tentativi di inviare la richiesta. Se non viene rilevata connettività Internet, eventuali ulteriori richieste attenderanno che venga rilevata.
Istruzioni per il debug
L'arresto di una sessione di debug in Microsoft Visual Studio è paragonabile alla chiusura dell'app: i caricamenti PUT vengono sospesi e i caricamenti POST vengono terminati. Anche durante il debug, l'app deve enumerare e quindi riavviare o annullare qualsiasi caricamento persistente. Puoi fare in modo, ad esempio, che l'app annulli le operazioni di caricamento persistenti enumerate all'avvio dell'app se le operazioni precedenti non sono interessanti per tale sessione di debug.
Mente si enumerano i download/caricamenti all'avvio dell'app durante una sessione di debug, puoi fare in modo che l'app li annulli se le operazioni precedenti non sono interessanti per tale sessione di debug. Se si verificano degli aggiornamenti a progetti Visual Studio, quali modifiche al manifesto dell'app e successivamente l'app viene disinstallata e ridistribuita, GetCurrentUploadsAsync non può enumerare le operazioni create usando la precedente distribuzione dell'app.
Per altre informazioni, vedi Debug e test delle app di Windows Store.
Se usi Trasferimento in background durante lo sviluppo, è possibile che le cache interne delle operazioni di trasferimento attive e completate perdano la sincronizzazione. Ciò può impedire l'avvio di nuove operazioni di trasferimento o l'interazione con le operazioni esistenti e gli oggetti BackgroundTransferGroup. In alcuni casi il tentativo di interagire con le operazioni esistenti può generare un arresto anomalo. Questo esito può verificarsi se la proprietà TransferBehavior è impostata su Parallel. Questo problema si verifica solo in alcuni scenari durante lo sviluppo e non è applicabile agli utenti finali dell'app.
Quattro scenari di Visual Studio possono causare questo problema.
- Crei un nuovo progetto con lo stesso nome di app di un progetto esistente ma in un linguaggio diverso (ad esempio, da C++ a C#).
- Modifichi l'architettura di destinazione (ad esempio, da x86 a x64) in un progetto esistente.
- Modifichi la lingua (ad esempio, da una lingua non associata ad alcun paese a en-US) in un progetto esistente.
- Aggiungi o rimuovi una funzionalità nel manifesto del pacchetto (ad esempio, aggiungendo Autenticazione Enterprise) in un progetto esistente.
Le normali operazioni di manutenzione dell'app, inclusi gli aggiornamenti del manifesto che aggiungono o rimuovono funzionalità, non attivano questo problema nelle distribuzioni dell'app per l'utente finale.
Per evitare il problema, disinstalla completamente tutte le versioni dell'app e ridistribuiscila con il nuovo linguaggio, la nuova architettura, la nuova lingua o la nuova funzionalità. Puoi eseguire questa operazione tramite la schermata Start oppure usando PowerShell e il cmdlet Remove-AppxPackage.
Riepilogo e passaggi successivi
In questo argomento abbiamo analizzato come caricare file tramite le API Background Transfer in JavaScript.
È anche possibile scaricare file nell'app di Windows Store. Per una spiegazione dei concetti di base ed esempi, vedi Come scaricare un file.
Argomenti correlati
Altro
Accesso alle informazioni relative a connessione e piano dati
Programmazione asincrona in JavaScript con le promesse
Creare la prima app di Windows Runtime in JavaScript
Come configurare le funzionalità di rete
Come scaricare un file con WinJS xhr
Riferimento
Windows.Networking.BackgroundTransfer
Esempi
Esempio di trasferimento in background