Server statiske ressourcer med foråret

1. Oversigt

Denne artikel udforsker, hvordan man gør det tjene statiske ressourcer med Spring - ved hjælp af både XML- og Java-konfiguration.

2. Brug af Spring Boot

Spring Boot leveres med en forudkonfigureret implementering af ResourceHttpRequestHandler for at lette betjening af statiske ressourcer.

Som standard serverer denne handler statisk indhold fra en hvilken som helst af / statisk, / offentlig, / ressourcer, og / META-INF / ressourcer mapper, der er på klassestien. Siden src / main / ressourcer er typisk på klassestien som standard, kan vi placere nogen af ​​disse mapper der.

For eksempel hvis vi lægger en om.html fil inde i / statisk i vores klassesti, så kan vi få adgang til den fil via //localhost:8080/about.html. På samme måde kan vi opnå det samme resultat ved at tilføje den fil i andre nævnte kataloger.

2.1. Tilpassede sti-mønstre

Som standard serverer Spring Boot alt statisk indhold under roddelen af ​​anmodningen, det vil sige /**. Selvom det ser ud til at være en god standardkonfiguration, vi kan ændre det via spring.mvc.static-path-mønster konfigurationsegenskab.

For eksempel, hvis vi vil have adgang til den samme fil via //localhost:8080/content/about.html, vi kan sige det i vores application.properties:

spring.mvc.static-path-pattern = / indhold / **

I WebFlux-miljøer skal vi bruge spring.webflux.static-path-mønster ejendom.

2.2. Brugerdefinerede mapper

Svarende til sti mønstre, det er også muligt at ændre standardressourceplaceringerne via spring.resources.static-locations konfigurationsegenskab. Denne egenskab kan acceptere flere komma-adskilte ressourceplaceringer:

spring.resources.static-locations = classpath: / files /, classpath: / static-files

Her serverer vi statisk indhold fra / filer og / statiske filer mapper inde i klassestien. I øvrigt, Spring Boot kan servere statiske filer uden for klassestien:

spring.resources.static-locations = fil: / opt / filer 

Her bruger vi filressource signaturen, fil:/, for at servere filer fra vores lokale disk.

3. XML-konfiguration

Hvis du har brug for at gå den gamle måde med XML-baseret konfiguration, kan du gøre god brug af mvc: ressourcer element for at pege på placeringen af ​​ressourcer med et specifikt offentligt URL-mønster.

For eksempel - den følgende linje vil tjene alle anmodninger om ressourcer, der kommer ind med et offentligt URL-mønster som “/ ressourcer / **”Ved at søge i“ /ressourcer /”-Mappe under rodmappen i vores applikation.

Nu kan vi få adgang til en CSS-fil som på følgende HTML-side:

Eksempel 3.1.

 Hjem 

4. Den ResourceHttpRequestHandler

Forår 3.1. introducerede ResourceHandlerRegistry at konfigurere ResourceHttpRequestHandlers til betjening af statiske ressourcer fra klassestien, WAR eller filsystemet. Vi kan konfigurere ResourceHandlerRegistry programmatisk inde i vores webkontekstkonfigurationsklasse.

4.1. Servering af en ressource, der er gemt i krigen

For at illustrere dette bruger vi den samme URL som før til at pege på myCss.css, men nu vil den faktiske fil være placeret i WAR'erne webapp / ressourcer mappe, hvor statiske ressourcer skal placeres, når der installeres Spring 3.1+ applikationer:

Eksempel 4.1.1.

@Configuration @EnableWebMvc public class MvcConfig implementerer WebMvcConfigurer {@Override public void addResourceHandlers (ResourceHandlerRegistry registry) {registry .addResourceHandler ("/ resources / **") .addResourceLocations ("/ resources /"); }}

Lad os analysere eksemplet bit. Først konfigurerer vi den URI-sti, der vender udefra, ved at tilføje definerer en ressourcehåndterer. Derefter kortlægger vi den udvendige URI-sti internt til den fysiske sti, hvor ressourcerne faktisk er placeret.

Vi kan selvfølgelig definere flere ressourcehåndterere ved hjælp af denne enkle, men alligevel fleksible API.

Nu - den følgende linje i en html side ville give os den myCss.css ressource inde i webapp / ressourcer vejviser:

4.2. Servering af en ressource, der er gemt i filsystemet

Lad os sige, at vi vil tjene en ressource, der er gemt i / opt / filer / katalog, når der kommer en anmodning om den offentlige URL, der matcher mønsteret: / filer / **. Vi konfigurerer simpelthen URL-mønsteret og kortlægger det til den bestemte placering på disken:

Eksempel 4.2.1.

@Override public void addResourceHandlers (ResourceHandlerRegistry registry) {registry .addResourceHandler ("/ files / **") .addResourceLocations ("file: / opt / files /"); }

* (For Windows-brugere: Argumentet videregivet til addResourceLocations for dette eksempel ville være “fil: /// C: / opt / filer /“).

Når vi har konfigureret ressourceplaceringen, kan vi bruge det kortlagte URL-mønster i vores hjem.html til indlæse et billede, der er gemt i filsystemet som følger:

Eksempel 4.2.2.

 Hjem 

4.3. Konfiguration af flere placeringer for en ressource

Hvad hvis vi vil lede efter en ressource mere end et sted?

Vi kan inkludere flere placeringer med addResourceLocations metode. Listen over placeringer søges i rækkefølge, indtil ressourcen er fundet. Lad os se på eksempel 3.3.1.

Eksempel 4.3.1

@Override public void addResourceHandlers (ResourceHandlerRegistry registry) {registry .addResourceHandler ("/ resources / **") .addResourceLocations ("/ resources /", "classpath: / other-resources /"); }

Den følgende krølleanmodning viser Hej.html side gemt i enten applikationens webappp / ressourcer eller den andre ressourcer mappe i klassestien.

krølle -i //localhost:8080/handling-spring-static-resources/resources/Hello.html

5. Det nye ResourceResolvers

Forår 4.1. giver - det nye RessourcerResolvere - forskellige typer ressourceopløsere, der kan bruges til at optimere browserens ydeevne ved indlæsning af statiske ressourcer. Disse resolvere kan lænkes og cachelagres i browseren for at optimere anmodningshåndtering.

5.1. Det PathResourceResolver

Dette er den enkleste løsning, og formålet er at finde en ressource, der får et offentligt URL-mønster. Faktisk, hvis nej ResourceResolver tilføjes til ResourceChainRegistration, dette er standardopløseren.

Lad os se et eksempel:

@Override public void addResourceHandlers (ResourceHandlerRegistry registry) {registry .addResourceHandler ("/ resources / **") .addResourceLocations ("/ resources /", "/ other-resources /") .setCachePeriod (3600) .resourceChain (true). addResolver (ny PathResourceResolver ()); }

Ting at bemærke:

  • Vi registrerer PathResourceResolver i ressourcekæden som eneste ResourceResolver i det. Se afsnit 4.3. for at kontrollere, hvordan man kæder mere end en ResourceResolver.
  • De serverede ressourcer gemmes i browseren i 3600 sekunder.
  • Kæden er endelig konfigureret med metoden resourceChain (sand).

Nu - HTML-koden, der i forbindelse med PathResourceResolver, lokaliserer foo.js script i enten webapp / ressourcer af webapp / andre ressourcer folder:

5.2. Det EncodedResourceResolver

Denne resolver forsøger at finde en kodet ressource baseret på Accept-kodning anmodning om overskriftsværdi.

For eksempel kan det være nødvendigt at optimere båndbredden ved at betjene den komprimerede version af en statisk ressource ved hjælp af gzip indholdskodning.

For at konfigurere en EncodedResourceResolver, vi skal bare konfigurere det i ResourceChain ligesom vi konfigurerede PathResourceResolver, som i følgende linje kode:

registry .addResourceHandler ("/ other-files / **") .addResourceLocations ("file: / Users / Me /") .setCachePeriod (3600) .resourceChain (true) .addResolver (new EncodedResourceResolver ());

Som standard er EncodedResourceResolver er konfigureret til at understøtte br og gzip kodninger.

Så følgende krølle anmodning får den zip-version af Hjem.html fil placeret i filsystemet i Brugere / mig / vejviser:

krølle -H "Accepter-kodning: gzip" //localhost:8080/handling-spring-static-resources/other-files/Hello.html

Læg mærke til hvordan vi sætter overskriftens “Accept-kodning”Værdi til gzip - dette er vigtigt, fordi netop denne resolver kun starter, hvis gzip-indholdet er gyldigt for svaret.

Til sidst skal du bemærke, at den komprimerede version forbliver tilgængelig i samme periode som i den periode, den cachelagres i browseren - hvilket i dette tilfælde er 3600 sekunder.

5.3. Lænkning ResourceResolvers

For at optimere ressourceopslag ResourceResolvers kan delegere håndteringen af ​​ressourcer til andre resolvere. Den eneste resolver, der ikke kan delegere til kæden, er PathResourceResolver som skal tilføjes i slutningen af ​​kæden.

Faktisk, hvis resourceChain er ikke indstillet til rigtigt, så som standard kun a PathResourceResolver vil blive brugt til at betjene ressourcer. I eksempel 4.3.1. vi kæder PathResourceResolver for at løse ressourcen, hvis GzipResourceResolver mislykkes.

Eksempel 5.3.1.

@Override offentligt ugyldigt addResourceHandlers (ResourceHandlerRegistry registry) {registry .addResourceHandler ("/ js / **") .addResourceLocations ("/ js /") .setCachePeriod (3600) .resourceChain (true) .addResolver (new GzipResourceResolver.) addResolver (ny PathResourceResolver ()); }

Nu hvor vi har tilføjet / js / ** mønster til ResourceHandler, lad os medtage foo.js ressource placeret i webapp / js / bibliotek i vores hjem.html side som i eksempel 4.3.2.

Eksempel 5.3.2.

 Hjem 

Det er værd at nævne, at fra og med Spring Framework 5.1, GzipResourceResolver er udfaset til fordel for EncodedResourceResolver. Derfor bør vi undgå at bruge det i fremtiden.

6. Yderligere sikkerhedskonfiguration

Hvis du bruger Spring Security - er det vigtigt at give adgang til statiske ressourcer. Vi bliver nødt til at tilføje de tilsvarende tilladelser for at få adgang til ressource-URL:

7. Konklusion

I denne artikel har vi illustreret forskellige måder, hvorpå en Spring-applikation kan tjene statiske ressourcer.

Den XML-baserede ressourcekonfiguration er en "arv" -mulighed som vi kan bruge, hvis vi endnu ikke kan gå ned på Java-konfigurationsruten.

Forår 3.1. kom ud med et grundlæggende programmatisk alternativ gennem dets ResourceHandlerRegistry objekt.

Og endelig - det nye ud af kassen ResourceResolvers og ResourceChainRegistration objekt leveres med Spring 4.1. tilbyde funktioner til optimering af ressourceindlæsning som caching og kæde af ressourcehåndtering for at forbedre effektiviteten i betjening af statiske ressourcer.

Som altid er det fulde eksempel tilgængeligt på Github. Derudover er Spring Boot-relaterede kildekoder også tilgængelige i dette projekt.