Récemment, mon collègue m'a demandé si j'avais des livres électroniques sur la technologie. J'ai ouvert la petite bibliothèque sur mon ordinateur, mais l'e-mail était trop important pour l'envoyer, et la société a interdit le partage avec des dossiers, alors j'ai passé une demi-journée à écrire un petit programme de téléchargement de fichiers et à le déployer sur ma machine Linux.
Fournir des fonctions: 1. Téléchargement de fichiers 2. Affichage et téléchargement de la liste des fichiers
La pièce téléchargée d'origine est laide. J'ai écrit du code JS pour l'optimiser. L'interface finale est indiquée comme suit:
Donnez d'abord les résultats, et ci-dessous montrera comment les implémenter étape par étape.
1. Créez un nouveau projet
La première chose est de créer un nouveau projet Spring-Boot. Vous pouvez choisir d'initialiser un projet sur le site Web ou d'utiliser la fonction printanière de l'IDE, et vous pouvez créer un nouveau projet. Ici, je crée un nouveau projet à partir de l'idée:
Ensuite, entrez le groupe et l'artefact et continuez à cliquer sur Suivant:
À l'heure actuelle, cette interface de sélection de module apparaît. Cliquez sur l'option Web et vérifiez le Web pour prouver qu'il s'agit d'un WebApp. Cliquez ensuite sur les moteurs de modèle pour sélectionner le moteur de modèle frontal. Nous choisissons le thymleaf. Spring-Boot Officiel recommande également d'utiliser ce modèle au lieu de JSP.
La dernière étape, puis attendez que le projet soit initialisé avec succès.
2. Paramètres de POM
Tout d'abord, vérifiez les dépendances dont vous devez ajouter au projet et publier directement mon fichier POM:
<? xml version = "1.0" Encoding = "utf-8"?> <project xmlns = "http://maven.apache.org/pom/4.0.0" xmlns: xsi = "http://www.w3.org/2001/xmlschema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.shuqing28</groupId> <artifactId>upload</artifactId> <version> 0.0.1-snapshot </ version> <packaging> jar </packaging> <name> upload </name> <description> Projet de démonstration pour Spring Boot </ Description> <parent> <proupId> org.springframework.boot </prouprid> <Artifactid> Spring-Boot-starter-Parent </ ArtifActid> <version> 1.5.9.9.Release </ Version> </ ArtifActid> <version> 1.5.9.9.Rease <! - Recherche parent du référentiel -> </parent> <properties> <project.build.sourceencoding> utf-8 </project.build.sourceencoding> <project.reportting.outputending> utf-8 </project.report.outputerSice> <java.version> 1.8 </java.version> <dependency> <proupId> org.springframework.boot </proupId> <ArtifactId> printemps-boot-starter </ artifactid> </dendency> <dependency> <proupId> org.springframework.boot </proupatid> <aRtifactid> Spring-boot-starter-thyleleaf </ artifactid> </dependence> <GroupId> org.springframework.boot </proupId> <Artifactid> printemps-boot-configuration-processor </ artifactid> <Apultal> true </acultational> </pedigency> <dependency> <proupId> org.springframework.boot </proupId> <ArtifActid> Spring-boot-starter-starter-Tesst </ artifact> <scope> test </cope> </dependency> <! - https://mvnrepository.com/artifact/org.webjars/bootstrap -> <dependency> <proupId> org.webjars </proupId> <Artifactid> bootstrap </ artifactid> <version> 3.3.5 </DERVIERSE> </Dedency> https://mvnrepository.com/artifact/org.webjars.bower/jquery -> <dependency> <proupId> org.webjars.bower </rom grouped> <ArtefactId> jQuery </letefactId> <Derson> 2.2.4 </De version> </Dedency> </Dependance> <Cuild> <frigins> <GroupId> org.springframework.boot </prôdId> <ArtefactId> Spring-Boot-Maven-Plugin </ ArfactId> </Glugin> </Glugins> </ Build> </ Project>
Vous pouvez voir que Spring-Boot-Starter-Thymeleaf contient WebApp, et les deux derniers webjars intègrent Bootstrap et JQuery, et d'autres codes seront utilisés.
Le dernier plugin Maven de démarrage de printemps est ajouté lorsque le système est créé, et il a les avantages suivants:
1. Il peut emballer tous les pots sous ClassPath et créer un "über-jar" exécutable pour faciliter les utilisateurs pour transférer des services.
2. Recherchez automatiquement la méthode du public statique void main () et marquez-la comme une classe exécutable
3. Selon la version Spring-Boot, une explication de dépendance intégrée est fournie.
3. Télécharger le contrôleur de fichiers
Si vous utilisez simplement SpringMVC pour télécharger des fichiers, vous devez configurer un haricot multipartrersolver ou configurer un <multipart-Config> dans web.xml, mais avec l'aide de la configuration automatique de Spring-Boot, vous n'avez rien à faire. Pour écrire directement la classe Controller, nous créons un nouveau package de contrôleur sous SRC / Main / Java et créons un nouveau fichierploadContrller:
package com.shuqing28.upload.controller; import com.shuqing28.uploadfiles.pojo.linker; import com.shuqing28.uploadfiles.exceptions.storagefilenotfoundException; import com.shuqing28.uploadfiles.svice.storageService; Import org.springframework.beans.factory.annotation.autowired; import org.springframework.core.io.resource; import org.springframework.http.httpheaders; org.springframework.ui.model; import org.springframework.web.bind.annotation. *; import org.springframework.web.multipart.multipartfile; import org.springframework.web.servlet.mvc.Method.annotation.mvcuriComponentsbuilder; org.springframework.web.servlet.mvc.support.redirectattributes; importer java.io.ioexception; import java.util.list; import java.util.stream.collector; @ControllerPublic class class Fileplower {private final starservice; @Autowired Public FileUploadController (StorageService StorageService) {this.storageService = StorageService; } @Getmapping ("/") public String listUploadFiles (modèle modèle) lève ioException {list <en linker> linkers = storageService.loadall (). Map (path -> new linker (mvcuricomponentsbuilder.frommethodname (fileuploadController.class, "ServeFile", path.getFileName (). toString ()). build (). toString (), path.getFileName (). toString ())) .Collect (collecors.tolist ()); Model.AddAttribute ("Linkers", Linkers); return "uploadform"; } @GetMapping ("/ Files / {FileName:. +}") @ResponseBody Public ResponseNtity <Source> ServeFile (@Pathvariable String fileName) {Resource File = StorageService.LoadasResource (FileName); return Responsentity.ok (). En-tête (httpheaders.content_disposition, "pièce jointe; filename = /" "+ file.getFileName () +" /"").body(file); } @Postmapping ("/") Public String HandleFilePload (@RequestParam ("Fichier") Fichier multipartFile, RedirectAttributes RedirectAttributes) {StorageService.Store (fichier); redirectattributes.addflashattribute ("message", "vous avez téléchargé avec succès" + file.getoriginalFileName () + "!"); retourner "rediriger: /"; } @ExceptionHandler (StorageFileNotFoundException.class) Public Responsentity <?> HandleStorageFileNotFound (StorageFilenotFoundException Exc) {return réponsentity.notFound (). Build (); }}L'annotation @Controller est ajoutée à la définition de la classe, prouvant qu'il s'agit d'un contrôleur. Chaque méthode est ajoutée avec @GetMapping et @postmapping correspondant respectivement aux demandes et publient respectivement.
Tout d'abord, @getMapping ("/"), Method listuploadfiles, comme le nom l'indique, affiche la liste de fichiers. Ici, nous utilisons StorageService pour traverser tous les fichiers du dossier et utilisons la méthode MAP pour synthétiser la liste des liens et des noms de fichiers, renvoyant un tableau d'objets de linker. L'objet de linker est un simple Pojo, qui ne contient que les deux parties suivantes:
FileUrl de chaîne privée; nom de fichier de chaîne privée;
Cette méthode comprend l'utilisation du flux dans Java8. Si vous ne comprenez pas, vous pouvez lire cet article sur les fonctionnalités Java8 en détail (ii) Stream API.
Ensuite, @GetMapping("/files/{filename:.+}") , Qui est ServiceFile, qui fournit une fonction de téléchargement de fichiers, ou utilise StorageService, et le code de réserve de stockage sera publié plus tard. Enfin, utilisez Responsentity pour retourner le fichier en tant que corps à la partie demandant.
Le manchefileupload de @PostMapping("/") utilise la demande de publication pour télécharger des fichiers. Le paramètre @RequestParam ("Fichier") extrait l'objet de fichier dans la demande de page Web, ou utilise StockerService pour enregistrer l'objet, et utilise enfin Redirection pour actualiser la page Web et donne le message téléchargé avec succès.
4. Traitement de fichiers
De nombreuses méthodes appelées par le contrôleur ci-dessus sont fournies par StorageService. Nous définissons une interface qui contient les méthodes suivantes:
package com.shuqing28.uploadfiles.service; import org.springframework.core.io.resource; import org.springframework.web.multiplart.multipartfile; import java.nio.file.path; import java.util.stream.stream; interface publique standardervice {void init ();); VOID Store (fichier multipartfile); Stream <Athath> Loadall (); Path Load (String File Name); Resource LoadAsResource (String FileName); void Deleteall ();}Parce que j'utilise simplement le système de fichiers local pour traiter les téléchargements à long terme de fichiers, j'ai la classe d'implémentation suivante:
package com.shuqing28.uploadfiles.service; import com.shuqing28.uploadfiles.exceptions.storageException; import com.shuqing28.uploadfiles.exception.storageFilenotFoundException; import com.shuqing28.uploadfiles.config.storageproperties; org.springframework.beans.factory.annotation.autowired; import org.springframework.core.io.resource; import org.springframework.core.io.urlresource; import org.springframework.sterreeotype.Service; import org.springframework. org.springframework.util.stringutils; import org.springframework.web.multiparpart.multipartfile; import java.io.nio.file.file.net.malformedUrlexception; java.nio.file.paths; importer java.nio.file.standardCopyOption; import java.util.stream.stream; @servicepublic class FileSystemStorageService implémente SterageService {private Final Path RootLocation; @Autowired public FileSystemStorageService (StorageProperties Properties) {this.rootlocation = paths.get (Properties.getLocation ()); } @Override public void init () {try {files.CreateDirectories (rootLocation); } catch (ioException e) {throw new StorageException ("n'a pas pu initialiser le stockage", e); }} @Override public void Store (fichier multipartFile) {String filename = stringUtils.cleanpath (file.getoriginalFileName ()); essayez {if (file.isempty ()) {throw new StorageException ("Échec du fichier vide" + nom de fichier); } if (fileName.Contains ("..")) {// Ceci est un contrôle de sécurité New StorageException ("Impossible de stocker le fichier avec un chemin relatif en dehors du répertoire actuel" + FileName); } Files.copy (file.getInputStream (), this.rootlocation.resolve (filename), standardCopyOption.replace_existing); } catch (ioException e) {Throw New StorageException ("Échec du fichier" + nom de fichier, e); }} @Override public Stream <Athath> loadall () {try {return files.walk (this.rootlocation, 1) .filter (path ->! Path.equals (this.rootlocation)) .map (path-> this.rootlocation.relatiVize (path)); } catch (ioException e) {lancez new StorageException ("Échec de la lecture de fichiers stockés", e); }} @Override Public Path Load (String FileName) {return rootLocation.Resolve (FileName); } @Override Public Resource LoadAsResource (String FileName) {try {path file = losh (filename); Ressource ressource = new UrlResource (file.touri ()); if (ressource.exists () || Resource.isReadable ()) {return Resource; } else {Throw New StorageFileNotFoundException ("n'a pas pu lire le fichier:" + nom de fichier); }} catch (MalformEdUrException e) {Throw New StorageFileNotFoundException ("Impossible de lire le fichier:" + FileName, E); }} @Override public void DeleteAll () {FileSystemUtils.deleterEcursively (rootlocation.tofile ()); }}Cette classe utilise également essentiellement le NIO de Java et utilise l'objet Path pour définir le chemin d'enregistrement par défaut pour l'emplacement du fichier.
Regardons d'abord la méthode du magasin. Le magasin accepte un objet multipartfile en tant que paramètre. Comparé au JSP traditionnel, il ne fait que passer des tableaux d'octets binaires. MultipartFile fournit de nombreuses méthodes pratiques à appeler, afin que nous puissions obtenir diverses informations sur le fichier téléchargé:
Interface publique MultipartFile étend InputStreamsource {String getName (); String GetoriginalFileName (); String getContentType (); booléen iSempty (); long getSize (); octet [] getBytes () lève ioException; InputStream getInputStream () lève ioException; void transfertto (fichier dest) lève IOException, illégalStateException;} Le code utilise la méthode de copie de fichiers pour copier le flux de fichiers sur le chemin d'accès correspondant à l'emplacement. Bien sûr, nous pouvons également utiliser la méthode Transferto pour enregistrer le fichier, file.transferTo(this.rootLocation.resolve(filename).toFile());
La méthode LoadAll charge toutes les informations de chemin de fichier dans ce chemin, LoadAsResource charge le fichier en tant qu'objet de ressource, puis examinez le code du contrôleur et accepte enfin un objet de ressource en tant que corps pour revenir au demandeur.
5. Modèle frontal
Enfin, le modèle frontal est défini, et ici nous allons toujours regarder le code d'abord:
<html xmlns: th = "http://www.thymeleaf.org"> <éadf> <Title> Partager des fichiers </Title> </ head> <body> <div th: if = "$ {message}"> <h2 th: text = "$ {message}" /> </ div> <div> <form method = "post" Action = "/" ENCTYPE = "multipart / form-data"> <! - Component start -> <input type = "file" name = "file" style = "visibilité: Hidden; height: 0" /> <div> <div name = "fichier1"> <entrée type = "Text" Laceholder = 'Choisissez un fichier ...' /> <pander> <bouton = "Button"> Button " -> <div> <Button type = "soumi"> soumettre </ bouton> <bouton type = "réset"> reset </utton> </div> </ form> </div> <div> <ul> <li th: every = "linker: $ {linkers}"> <a th: href = "$ {linker.fileurl}" rel = "external nofollow" th: text = "$ {linker.filename}" /> </li> </ul> </ div> <script src = "// ajax.aspnetcdn.com/ajax/jquery/jquery-1.9.1.min.js"><</script><script src = "/ webjars / bootstrap / 3.3.5 / js / bootstrap.min.js"> </ script> <script type = "text / javaScript" th: inline = "javascript"> function bs_input_file () {$ (". input-file"). avant () {if (! $ (this) .prev (). {var élément = $ (". Input-ghost"); element.change (function () {élément.next (élément) .find ('entrée'). Val ((element.val (this). $ (this) .find ("Button.btn-reset"). Cliquez sur (fonction () {element.val (null); $ (this) .parents (". Input-file"). find ('input'). {$ (this) .parents ('. Input-File'). } $ (function () {bs_input_file ();}); </ script> <link rel = "Stylesheet" href = "/ webjars / bootstrap / 3.3.5 / css / bootstrap.min.css" rel = "external nofollow" /> </ body> </html>La chose importante ici est le contenu de la balise <form>. <form méthode = "post" Action = "/" EncType = "multipart / form-data"> ENCTYPE doit être écrit en multiparte / format de forme. Utilisez la publication pour télécharger des fichiers. Le contrôle de téléchargement d'origine est laid, j'ai donc fait une entrée de texte + et je l'ai placé sur la surface, et j'ai placé une entrée de fichier de téléchargement invisible ci-dessous. Vous pouvez regarder le code par vous-même, donc je n'en parlerai pas dans cet article.
Ici, nous plaçons également une liste pour afficher la liste des fichiers. Ici, nous obtenons l'objet Linkers fourni par le serveur. Par constamment foreach, nous pouvons obtenir les deux éléments de FileUrl et de nom de fichier.
Ici, JQuery a été remplacé par le CDN de Microsoft, et WebJars ne peut pas être présenté, donc je ne sais pas pourquoi.
Autres paramètres
Définissez la limite de taille du fichier de téléchargement dans SRC / Main / Resources / Application.Properties
printemps.http.multipart.max-file-size = 128mbbspring.http.multupart.max-request-size = 128Mb
De plus, le chemin de sauvegarde du fichier par défaut est également défini:
package com.shuqing28.uploadfiles.config; import org.springframework.boot.context.properties.configurationProperties; @configurationproperties ("Storage") public StorageProperties {private string location = "/ home / jenkins / upload-file /"; Public String getLocation () {return emplacement; } public void setLocation (string emplacement) {this.location = location; }}Notez ici qu'en raison du paramètre StorageProperties, vous devez l'ajouter à la classe d'application.
@EnableConfigurationProperties annotation @ SpringbootApplication @ perteConfigurationProperties (StorageProperties.class) public class uploadApplication {public static void main (String [] args); }}Résumer
Ce qui précède est le Spring Boot + Thymeleaf que l'éditeur vous a présenté pour réaliser la fonction de téléchargement de fichiers et de téléchargement. J'espère que cela vous sera utile. Si vous avez des questions, veuillez me laisser un message et l'éditeur vous répondra à temps. Merci beaucoup pour votre soutien au site Web Wulin.com!