Pagina 1 di 2 1 2 ultimoultimo
Visualizzazione dei risultati da 1 a 10 su 12
  1. #1
    Utente di HTML.it
    Registrato dal
    Jan 2007
    Messaggi
    655

    Servlet per il download del file

    Ciao a tutti, ho realizzato una servlet Java per la creazione di un file.

    Ora però non so come fare scaricare all'utente il file creato.

    Sapreste darmi qualche dritta su come poter far fare il download ?

    Grazie!

  2. #2
    Utente di HTML.it L'avatar di andbin
    Registrato dal
    Jan 2006
    residenza
    Italy
    Messaggi
    18,284
    Quote Originariamente inviata da melmar20 Visualizza il messaggio
    Ciao a tutti, ho realizzato una servlet Java per la creazione di un file.
    Dove è posizionato il file rispetto alla web application?

    Quote Originariamente inviata da melmar20 Visualizza il messaggio
    Ora però non so come fare scaricare all'utente il file creato.
    La soluzione è avere un'altra servlet che si occupa del download del file. Il principio basilare è che basta ottenere un InputStream del file e poi leggere a blocchi di byte e buttarli pari-pari sul OutputStream (il ServletOutputStream della response, che è-un OutputStream).
    Però bisogna anche settare degli header in modo appropriato. Sicuramente il Content-Type affinché un client possa dedurre come trattare il documento. Se vuoi che qualunque browser faccia il download senza sapere altro, si può usare il content type "application/octet-stream".
    Poi visto che è un file e sai a priori la lunghezza, sarebbe anche utile ed appropriato impostare il header Content-Length.
    Si può anche impostare il Content-Disposition per indicare che è un attachment con un certo nome specifico.
    Poi si possono facoltativamente impostare altri header per permettere o impedire il caching.

    Per lo streaming si possono anche usare metodi di librerie apposite come la Apache Commons IO che ha una classe FileUtils con un comodissimo metodo public static long copyFile(File input, OutputStream output)
    Ultima modifica di andbin; 25-11-2016 a 10:34
    Andrea, andbin.devSenior Java developerSCJP 5 (91%) • SCWCD 5 (94%)
    java.util.function Interfaces Cheat SheetJava Versions Cheat Sheet

  3. #3
    Utente di HTML.it
    Registrato dal
    Jan 2007
    Messaggi
    655
    Ciao, il file di cui voglio fare il download è un file Excel creato con la libreria Apache POI, non mi interessa memorizzarlo su server.
    codice:
    		response.setContentType(
    "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");        
    response.setHeader("Content-Disposition", "attachment; filename=excel.xlsx");
    
    OutputStream out = response.getOutputStream();
    workbook.write(out);
    workbook.close();
    out.flush();
    out.close();
    Ma non funziona.

  4. #4
    Moderatore di Programmazione L'avatar di LeleFT
    Registrato dal
    Jun 2003
    Messaggi
    17,320
    Innanzitutto l'OutputStream che ottieni dalla response non va chiuso. Quell'OutputStream è gestito dall'Application Server / Servlet Container, è lui che si deve occupare della chiusura.

    Poi dici che non funziona: controlla i log per vedere se vi è qualche eccezione ed, eventualmente, postala qui. Al di là del content-type (che io imposto solitamente a "application/octet-stream;name=...") non vedo problemi nel codice che hai postato.


    Ciao.
    "Perchè spendere anche solo 5 dollari per un S.O., quando posso averne uno gratis e spendere quei 5 dollari per 5 bottiglie di birra?" [Jon "maddog" Hall]
    Fatti non foste a viver come bruti, ma per seguir virtute e canoscenza

  5. #5
    Utente di HTML.it L'avatar di andbin
    Registrato dal
    Jan 2006
    residenza
    Italy
    Messaggi
    18,284
    Il problema può essere il fatto di non aver inviato il Content-Length, perlomeno con certi browser ci potrebbe essere.

    Quindi:
    - scarichi il documento su un file temporaneo, poi sapendo la lunghezza invii il Content-Length e poi fai lo streaming in output del file.
    oppure
    - scarichi il documento in memoria su un ByteArrayOutputStream, poi sapendo la lunghezza invii il Content-Length e poi fai lo streaming in output del ByteArrayOutputStream usando il suo writeTo(OutputStream out).

    A tua scelta ....
    Andrea, andbin.devSenior Java developerSCJP 5 (91%) • SCWCD 5 (94%)
    java.util.function Interfaces Cheat SheetJava Versions Cheat Sheet

  6. #6
    Utente di HTML.it
    Registrato dal
    Jan 2007
    Messaggi
    655
    Ok, non ho chiuso l'OutputStream ed ho impostato il content-type ad "application/octet-stream".

    Il log mi da solo "Inizializzazione riuscita", ma nulla ancora non riesco dal browser ad effettuare il download del file che ho scritto.

  7. #7
    Utente di HTML.it
    Registrato dal
    Jan 2007
    Messaggi
    655
    Ho provato la seconda strada scrivendo questo codice:
    codice:
    ByteArrayOutputStream outByteStream = 
    new ByteArrayOutputStream();
    
                workbook.write(outByteStream);
    
                
    byte [] outArray = outByteStream.toByteArray();
    
                response.setContentType(
    "application/OCTET-STREAM");
    
                response.setContentLength(outArray.
    length);
    
                response.setHeader(
    "Expires:", "0"); 
    
                response.setHeader(
    "Content-Disposition", "attachment; filename=testxls.xls");
    
                OutputStream outStream = response.getOutputStream();
    
                outStream.write(outArray);
    
                outStream.flush();
    
    ma ancora nulla!! il file testxls.xls no ne vuole sapere di essere scaricato

    Quote Originariamente inviata da andbin Visualizza il messaggio
    Il problema può essere il fatto di non aver inviato il Content-Length, perlomeno con certi browser ci potrebbe essere.

    Quindi:
    - scarichi il documento su un file temporaneo, poi sapendo la lunghezza invii il Content-Length e poi fai lo streaming in output del file.
    oppure
    - scarichi il documento in memoria su un ByteArrayOutputStream, poi sapendo la lunghezza invii il Content-Length e poi fai lo streaming in output del ByteArrayOutputStream usando il suo writeTo(OutputStream out).

    A tua scelta ....

  8. #8
    Moderatore di Programmazione L'avatar di LeleFT
    Registrato dal
    Jun 2003
    Messaggi
    17,320
    Quote Originariamente inviata da melmar20 Visualizza il messaggio
    Il log mi da solo "Inizializzazione riuscita", ma nulla ancora non riesco dal browser ad effettuare il download del file che ho scritto.
    ?

    Non sto parlando dell'eventuale console dell'ambiente di sviluppo, ma del log del tuo Servlet Container (Tomcat) o del tuo Application Server dove gira la webapp. Ad esempio, Tomcat ha diversi file di log: un file dove logga tutti gli accessi, un file dove logga lo standard output, un file dove logga lo standard error (ed è qui che finiscono le eccezioni), un log di catalina, ecc...

    Vedi anche la risposta di andbin.

    Ciao.
    "Perchè spendere anche solo 5 dollari per un S.O., quando posso averne uno gratis e spendere quei 5 dollari per 5 bottiglie di birra?" [Jon "maddog" Hall]
    Fatti non foste a viver come bruti, ma per seguir virtute e canoscenza

  9. #9
    Utente di HTML.it L'avatar di andbin
    Registrato dal
    Jan 2006
    residenza
    Italy
    Messaggi
    18,284
    Quote Originariamente inviata da melmar20 Visualizza il messaggio
    codice:
    byte [] outArray = outByteStream.toByteArray();
    Di per sé NON serve ottenere un nuovo byte[] array ... semplicemente è uno spreco di risorse. ByteArrayOutputStream ha size() e il writeTo(OutputStream out) citato prima.

    Ma a parte lo "spreco" di memoria, non vedo nulla di palesemente/grossolanamente errato.

    Quote Originariamente inviata da melmar20 Visualizza il messaggio
    ma ancora nulla!!
    nulla in che senso?

    - la response è completamente vuota o c'è qualcosa?
    - se c'è qualcosa che cosa è? (analizzalo con un hex editor/viewer, eventualmente)
    - c'è qualche eccezione?
    Andrea, andbin.devSenior Java developerSCJP 5 (91%) • SCWCD 5 (94%)
    java.util.function Interfaces Cheat SheetJava Versions Cheat Sheet

  10. #10
    Utente di HTML.it
    Registrato dal
    Jan 2007
    Messaggi
    655
    Con nulla intendo che non succede nulla la response non restituisce nessun valore.
    Chiamo la servlet mediante questa chiamata Ajax:
    codice:
    $.ajax({
    
     
     
                url : 
    "CreaFileExcel",
    
                type : 
    "POST",
    
                data : {path:$(
    "#input_file").val()},
    
                async: 
    false,
    
                dataType :
    "json",
    
                processData: 
    false,  
    
                contentType: 
    false, 
    
                success: 
    function(msg)
    
                {
    
                     
    if(msg.esito!=null ) alert("Creato file Log_Errori.xlsx");
    
     
                     
     
    
     
                },
    
                error: 
    function (jqXHR, textStatus, errorThrown) {        
    alert("KO");
    
                    }
            });    
    
    e aimè , non viene visualizzata nessuna finestra di alert.
    Nella console non ho eccezioni e sul server non ho ancora trovalo il file di log dei messaggi di errore.

Permessi di invio

  • Non puoi inserire discussioni
  • Non puoi inserire repliche
  • Non puoi inserire allegati
  • Non puoi modificare i tuoi messaggi
  •  
Powered by vBulletin® Version 4.2.1
Copyright © 2025 vBulletin Solutions, Inc. All rights reserved.