2017-05-20 17 views
0

Ich habe etwas recherchiert, konnte aber nicht herausfinden, wie ich das lösen kann. Ich möchte die Möglichkeit geben, einige Datensätze aus meiner Datenbank nach CSV zu exportieren, wenn ein Benutzer klick auf "Datensätze ohne Mail-ID exportieren" klickt. Was ist der beste Weg, dies zu erreichen? In meiner Forschung finde ich heraus, dass Leute nur Servlets als Beispiele verwenden, aber für mich verwende ich keine Servlets.JSP und SPRING Boot: Generiere CSV-Datei von JSON-Eingabe?

Dies ist mein Controller:

@RequestMapping(value = "/eblnotif/exportMailId", method = RequestMethod.POST, produces = "application/json") 
     public @ResponseBody List<EblNotifResource> exportMailIdCsv(@RequestBody Filters filters) 
       throws IllegalAccessException, IllegalArgumentException, InvocationTargetException, NoSuchMethodException, 
       SecurityException, IOException { 

      List<EblNotif> eblnotif_list = accountSservice.exportMailIdCsv(filters); 

      List<EblNotifResource> eblnotifres = new ArrayList<>(); 

      for (EblNotif eblNotif : eblnotif_list) { 
       EblNotifResource eblres = new EblNotifResource(); 
       eblres.setFormName(eblNotif.getFormName()); 
       eblres.setSendingDate(eblNotif.getSendingDate()); 
       eblres.setMode(eblNotif.getMode()); 
       eblres.setLanguage(eblNotif.getLanguage()); 
       eblres.setGpart(eblNotif.getGpart()); 
       eblres.setEmail(eblNotif.getEmail()); 
       eblres.setMailId(eblNotif.getMailId()); 
       eblnotifres.add(eblres); 
      } 
      return eblnotifres; 
    } 
} 

Und gibt zurück an den Client (JSP) das JSON-Format:

[ 
    { 
     "formName":"FormName1", 
     "mode":"S", 
     "language":"F", 
     "sendingDate":"2017-04-03", 
     "gpart":"555", 
     "email":"", 
     "mailId":"96318" 
    }, 
    { 
     "formName":"FormName2", 
     "mode":"S", 
     "language":"F", 
     "sendingDate":"2017-04-03", 
     "gpart":"444", 
     "email":"", 
     "mailId":"96325" 
    } 
] 

Die im csv gewünschten Ausgang so etwas wie sein:

formName;mode;language;sendingDate;gpart;email;mailId 
FormName1;S;F;2017-04-03;555;[email protected];96318 
FormName2;S;F;2017-04-03;444;[email protected];96325 
+1

Warum konvertieren Sie es nicht in eine CSV-Datei in Ihrer Controller-Methode und geben die resultierende CSV-Zeichenfolge als Antworttext zurück? –

+0

Hallo danke für deine Antwort. Weil ich es nicht schaffen würde. Wenn ich es sofort in meinem Controller konvertiere, ist es auch gut. Können Sie mir bitte Links oder Beispiele nennen, wie Sie es erreichen können? Vielen Dank – algorithmic

Antwort

1

Es gibt eine Reihe von Möglichkeiten, um in eine CSV-Datei zu konvertieren, aber in eine Richtung

@RequestMapping(value = "/eblnotif/exportMailId", method = RequestMethod.POST, produces = "application/json") 
public @ResponseBody String exportMailIdCsv(@RequestBody Filters filters) throws IllegalAccessException, 
     IllegalArgumentException, InvocationTargetException, NoSuchMethodException, SecurityException, IOException { 

    List<EblNotif> eblnotif_list = accountSservice.exportMailIdCsv(filters); 

    String separator = ";"; 
    SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd"); 
    StringBuilder sb = new StringBuilder(); 
    sb.append("formName;mode;language;sendingDate;gpart;email;mailId").append(System.lineSeparator()); 
    for (EblNotif eblNotif : eblnotif_list) { 
     sb.append(eblNotif.getFormName()).append(separator); 
     sb.append(eblNotif.getMode()).append(separator); 
     sb.append(eblNotif.getLanguage()).append(separator); 
     sb.append(dateFormat.format(eblNotif.getSendingDate())).append(separator); 
     sb.append(eblNotif.getGpart()).append(separator); 
     sb.append(eblNotif.getEmail()).append(separator); 
     sb.append(eblNotif.getMailId()).append(separator); 
     sb.append(System.lineSeparator()); 
    } 
    return sb.toString(); 
} 
1

Verwendung von Apache Commons CSV Sie können wie etwas tun:

@RequestMapping(value = "/download/eblnotif") 
    public void download(@RequestBody @Valid Filters filter, 
         HttpServletResponse httpServletResponse) throws Exception { 
     List<EblNotifResource> resources = //find from the fitler 
     CSVPrinter csvPrinter = CSVWriterUtil.transformResourcesToCSVPrinter(new BufferedWriter(httpServletResponse.getWriter()), resources); 
     httpServletResponse.setHeader("Content-Disposition", "attachment; filename=\"file.csv\""); 
     csvPrinter.flush(); 
     csvPrinter.close(); 
    } 


    public final class CSVWriterUtil { 

    private static final String NEW_LINE_SEPARATOR = "\n"; 

    private CSVWriterUtil() { 
    } 

    public static CSVPrinter transformResourcesToCSVPrinter(Writer writer, List<EblNotifResource> eblNotifResources) { 
     try { 
      CSVPrinter csvPrinter = new CSVPrinter(new BufferedWriter(writer), CSVFormat.DEFAULT.withRecordSeparator(NEW_LINE_SEPARATOR)); 
      for (EblNotifResource eblNotifResource : eblNotifResources) { 
       List<String> dataRecords = new ArrayList<>(); 
       dataRecords.add(eblNotifResource.getFormName()); 
       dataRecords.add(eblNotifResource.getSendingDate()); 
       //...etc 
       csvPrinter.printRecord(dataRecords); 
      } 
      return csvPrinter; 
     } catch (IOException e) { 
      throw new SystemException("Exception occurred while converting file", e); 
     } 
    } 

} 
1

Wenn ein CSV-Download nur als einmaligen Fall erforderlich ist, ist die relevanten Objekte innerhalb der Controller-Methode Umwandlung wahrscheinlich die einfachste Möglichkeit, . Wenn ein solcher Download jedoch an mehreren Stellen erforderlich ist, kann es vorteilhafter sein, Spring MVC Rest über eine HttpMessageConverter CSV-Unterstützung in der Zukunft hinzuzufügen.

Schritt 1: Optional, aber

empfohlen

eine CSV-Konvertierung Bibliothek verwenden wie OpenCSV, uniVocity oder Smooks (nur die CSV-Parser) Objekte in und aus CSV zu konvertieren. Die Verwendung einer guten Bibliothek spart eine Menge Standardcode und kann auch verwendet werden, um die Unterstützung für zusätzliche Formate wie Tab-separated-Werte (TSV) und Spalten mit fester Breite zu erweitern.

Schritt 2: Implementieren GenericHttpMessageConverter

eine Implementierung von GenericHttpMessageConverter Erstellen von Objekten ein bisschen schwierig auf Schritt 1 Dieser Schritt ausgewählt und von CSV mit der CSV-Bibliothek zur Konvertierung zu konvertieren ist, weil ein HttpMessageConverter wird normalerweise verwendet, um ein einzelnes Objekt in den gewünschten Inhaltstyp zu konvertieren, während CSV-Inhalt eine Sammlung von Objekten ist (jede Zeile repräsentiert ein Objekt). Das Spring-Team hat jedoch ein ausgezeichnetes Beispiel in Jaxb2CollectionHttpMessageConverter zum Konvertieren von Sammlungen von Objekten auf den gewünschten Inhaltstyp bereitgestellt. Folgende Punkte müssen im Auge behalten werden:

  1. Die boolean canRead(Class<?>, MediaType) Methode sollte immer gemacht werden, um das Rück false als CSV-Inhalt eine Sammlung von Objekten ist, damit es nicht zu einem einzigen Objekt angegeben durch eine Art gelesen werden kann.
  2. Die boolean canRead(Type, Class<?>, MediaType)-Methode sollte die Type untersuchen, um sicherzustellen, dass sie einen Collection-Typ angibt und dass der Typ der Elemente, die die Sammlung enthalten soll, ebenfalls angegeben wurde.
  3. Die Methode T read(Type, Class<?>, HttpInputMessage) sollte implementiert werden, um CSV-Inhalte zu lesen.
  4. Die Methode void write(T, Type, Class<?>, HttpInputMessage) sollte implementiert werden, um CSV-Inhalte zu schreiben.

Schritt 3: Die Meldung CSV-Wandler in der Konfiguration registriert werden sollte

@Override 
protected void configureMessageConverters(final List<HttpMessageConverter<?>> converters) 
{ 
    converters.add(csvMessageConverter()); 

    super.addDefaultHttpMessageConverters(converters); 
} 

Schritt 4: Controller Methoden sollten eine Sammlung der zurückgeführt werden erforderliche Objekte

public List<?> get() { ... } 

Eine Beispielanwendung ist on Github verfügbar dies in Aktion zeigt. Starten Sie die Anwendung und senden Sie dann Anforderungen an http://localhost:8080/persons.csv oder http://localhost:8080/persons.json, um Daten im CSV- oder JSON-Format abzurufen.