Wat is een filter?
Een filter is een functie van de J2EE-standaardspecificatie waarmee aanvullende taken kunnen worden verwerkt voor alle aanvragen die overeenkomen met een URL-patroon, vóór of nadat de aanvraag naar de dispatcher-servlet (Dispatcher Servlet) is verzonden. Met andere woorden, het wordt beheerd door een webcontainer zoals Tomcat, niet door de Spring-container, dus het verwerkt de aanvraag voordat deze naar de dispatcher-servlet gaat.
Filter implementeren
Om een filter toe te voegen, moet de javax.servlet Filter-interface worden geïmplementeerd. Deze interface heeft de volgende drie methoden.
- init-methode
- Deze methode initialiseert het filterobject en voegt het toe aan de service. De webcontainer roept de init-methode één keer aan om het filterobject te initialiseren. Vervolgens worden volgende aanvragen verwerkt via de doFilter()-methode.
- doFilter-methode
- Deze methode wordt uitgevoerd door de webcontainer voordat elke HTTP-aanvraag die overeenkomt met het url-patroon naar de dispatcher-servlet wordt verzonden en voordat de dispatcher-servlet een HTTP-antwoord naar de client stuurt.
De doFilter()-methode heeft een FilterChain als parameter. Via de doFilter()-methode van FilterChain wordt de aanvraag doorgegeven aan de volgende bestemming. Door de gewenste verwerking voor en na chain.doFilter() toe te voegen, kunnen we de gewenste verwerking uitvoeren.
- Deze methode wordt uitgevoerd door de webcontainer voordat elke HTTP-aanvraag die overeenkomt met het url-patroon naar de dispatcher-servlet wordt verzonden en voordat de dispatcher-servlet een HTTP-antwoord naar de client stuurt.
- destroy-methode
- Deze methode verwijdert het filterobject uit de service en geeft de gebruikte resources terug. De webcontainer roept deze methode één keer aan. Daarna wordt de aanvraag niet meer via doFilter() verwerkt.
Voorbeeldcode - Servlet-specificatie
Voorbeeldcode - @Component
- @Component: Filter kan als Spring-bean worden geregistreerd.
- @Order: Als er meerdere filters zijn, kan de volgorde worden ingesteld.
- Als een filter dat overeenkomt met de servlet-specificatie op deze manier als Spring-bean wordt geregistreerd, kunnen andere beans die overeenkomen met de Spring-specificatie worden gebruikt.
Voorbeeldcode - @Configuration
Als u wilt dat een filter alleen voor een bepaalde URI werkt, kunt u FilterRegistrationBean gebruiken om de filter als Spring-bean te registreren.
Filterdoeleinden
Het is voornamelijk verantwoordelijk voor het valideren en verwerken van aanvraagparameters zelf.
- Algemene taken met betrekking tot beveiliging
- Omdat een filter werkt in een webcontainer, kan het beveiligingscontroles (zoals XSS, CSRF-verdediging) uitvoeren en onjuiste aanvragen blokkeren. Omdat de aanvraag niet naar de Spring-container wordt verzonden en wordt geblokkeerd, kan de stabiliteit verder worden verbeterd.
- Loggen van alle aanvragen
- Afbeelding/gegevenscompressie en tekencodering
- Een filter implementeert functies die algemeen worden gebruikt in webapplicaties, zoals het comprimeren van afbeeldingen of gegevens en het coderen van tekenreeksen.
- ServletRequest aanpassen
- HttpServletRequest kan de inhoud van de body maar één keer lezen. Daarom kunnen Filter of Interceptor de body niet lezen. Een aangepaste ServletRequest kan worden gemaakt om de body te loggen.
Interceptor
Wat is een interceptor?
In tegenstelling tot filters (Filter), die een J2EE-standaardspecificatie zijn, is een interceptor (Interceptor) een technologie die door Spring wordt aangeboden. Hiermee kunnen aanvragen en antwoorden worden geraadpleegd of bewerkt vóór en nadat de dispatcher-servlet een controller aanroept. Met andere woorden, in tegenstelling tot filters, die werken in een webcontainer, werken interceptors in de Spring-context.
De dispatcher-servlet vraagt om de juiste controller te vinden via handler-mapping en retourneert een uitvoeringsketen (HandlerExecutionChain) als resultaat. Als er dus een of meer interceptors in deze uitvoeringsketen zijn geregistreerd, worden de interceptors opeenvolgend uitgevoerd en wordt de controller uitgevoerd. Als er geen interceptors zijn, wordt de controller direct uitgevoerd.
Interceptor implementeren
Om een interceptor toe te voegen, moet de org.springframework.web.servlet.HandlerInterceptor-interface worden geïmplementeerd. Deze interface heeft de volgende drie methoden.
- preHandle-methode
- De preHandle-methode wordt uitgevoerd voordat de controller wordt aangeroepen. Daarom kan deze worden gebruikt voor voorverwerkingsbewerkingen die moeten worden uitgevoerd voordat de controller wordt aangeroepen, of voor het verwerken of toevoegen van aanvraaginformatie.
- De derde parameter van de preHandle-methode, de handler-parameter, is een object dat de informatie van de methode met @RequestMapping abstract weergeeft.
- Het retourtype van de preHandle-methode is boolean. Als de retourwaarde true is, gaat het proces verder naar de volgende stap. Als het false is, wordt het proces gestopt en worden volgende stappen (de volgende interceptor of controller) niet uitgevoerd.
- postHandle-methode
- De postHandle-methode wordt uitgevoerd nadat de controller is aangeroepen. Deze kan dus worden gebruikt wanneer er nabewerkingen zijn die moeten worden uitgevoerd na de controller.
- afterCompletion-methode
- Zoals de naam al aangeeft, wordt de afterCompletion-methode uitgevoerd nadat alle bewerkingen zijn voltooid, inclusief het genereren van het uiteindelijke resultaat in alle views.
Voorbeeldcode
- De gemaakte interceptor wordt als bean geregistreerd.
- De gemaakte interceptor wordt geregistreerd in de addInterceptors()-methode van de WebMvcConfigurer-interface.
- Interceptors werken in de volgorde waarin ze zijn geregistreerd in InterceptorRegistry.
Interceptordoeleinden
Het is voornamelijk verantwoordelijk voor het verwerken van de consistentie van aanvraaginformatie met behulp van servicelogica.
- Algemene taken zoals authenticatie/autorisatie
- Typische taken met betrekking tot clients, zoals authenticatie of autorisatie, kunnen worden gecontroleerd voordat ze naar de controller gaan.
- Loggen van API-aanroepen
- Via de ontvangen HttpServletRequest- en HttpServletResponse-objecten kan informatie over de client worden geregistreerd.
- Gegevens verwerken die naar de controller worden doorgegeven
- De ontvangen HttpServletRequest- en HttpServletResponse-objecten kunnen worden verwerkt en doorgegeven aan de controller.
- AOP nabootsen
- Via de derde parameter van de preHandle()-methode, HandlerMethod, kan aanvullende informatie over de uit te voeren methode, zoals de handtekening van de methode, worden opgehaald om te bepalen of de logica moet worden uitgevoerd.
Filter vs. Interceptor
- Filters worden uitgevoerd in de webcontext en interceptors in de Spring-context, dus het uitvoeringspunt is anders.
- Filters kunnen de dispatcher-servlet vóór en na verwerken en interceptors kunnen de controller vóór en na verwerken.
- Filters zijn geschikt voor taken die onafhankelijk van Spring globaal moeten worden verwerkt of voor het valideren van de aanvraagparameters zelf, of wanneer ServletRequest in plaats van HttpServletRequest moet worden gebruikt.
- Interceptors zijn geschikt voor taken die globaal moeten worden verwerkt met betrekking tot clientverzoeken binnen Spring of wanneer servicelogica moet worden gemengd.
- U kunt uitzonderingen afhandelen met behulp van @ControllerAdvice en @ExceptionHandler in interceptors, maar niet in filters.
- Filters behandelen meestal uitzonderingen die zich voordoen op dat moment door de doFilter()-methode te omringen met een try~catch-instructie.
Argument Resolver
Wat is Argument Resolver?
Argument Resolver kan indirect helpen bij het maken van het gewenste object uit de waarde van een aanvraag wanneer er een aanvraag bij een controller binnenkomt.
Doeleinden van Argument Resolver
Stel bijvoorbeeld dat er een aanvraag met een JWT-token binnenkomt. We moeten het token valideren en vervolgens de id die in het token is opgeslagen ophalen om deze om te zetten naar een aangemeld gebruikersobject.
Zonder Argument Resolver moet deze validatie en conversie naar een aangemeld gebruikersobject in elke controller worden geïmplementeerd. Dit leidt tot redundante code in controllers waar gebruikersvalidatie vereist is, en de verantwoordelijkheid van de controller neemt toe. Argument Resolver kan dit probleem oplossen.
Argument Resolver implementeren
ArgumentResolver kan worden gebruikt door HandlerMethodArgumentResolver te implementeren. Deze interface geeft aan dat de volgende twee methoden moeten worden geïmplementeerd.
- supportsParameter-methode
- Een bepaalde annotatie wordt gemaakt en aan de parameter toegevoegd waarvoor ArgumentResolver moet worden uitgevoerd. De supportsParameter()-methode controleert of de ontvangen methode een parameter heeft met de gewenste annotatie en retourneert true als deze de gewenste annotatie bevat.
- resolveArgument-methode
- Als supportsParameter true retourneert, d.w.z. als er een methode is met een bepaalde annotatie, is dit de methode die de parameter bindt aan de gewenste vorm en retourneert.
Als ArgumentResolver op deze manier wordt gebruikt, ziet de implementatie van de controller er als volgt uit.
Verschil tussen Argument Resolver en Interceptor
- ArgumentResolver werkt na de interceptor en retourneert het gewenste object uit de waarde van een aanvraag wanneer er een aanvraag bij een controller binnenkomt.
- Aan de andere kant onderschept een interceptor het verzoek voordat de controller daadwerkelijk wordt uitgevoerd en kan het geen bepaald object retourneren. Alleen het retourtype boolean of void bestaat.
Bron
- https://mangkyu.tistory.com/173
- https://junhyunny.github.io/spring-boot/filter-interceptor-and-aop/
- https://supawer0728.github.io/2018/04/04/spring-filter-interceptor/
- https://tecoble.techcourse.co.kr/post/2021-05-24-spring-interceptor/
- https://baeldung-cn.com/spring-mvc-handlerinterceptor-vs-filter
- https://www.baeldung.com/spring-boot-add-filter
Verwachte interviewvragen en antwoorden
Wat is een filter?
Een filter biedt de mogelijkheid om aanvullende taken te verwerken voor alle aanvragen die overeenkomen met een URL-patroon, vóór of nadat de aanvraag naar de dispatcher-servlet is verzonden, en werkt op containerniveau van de servlet.
Wanneer wordt een filter gebruikt?
Filters kunnen worden gebruikt om taken uit te voeren die onafhankelijk van Spring globaal moeten worden verwerkt. Of wanneer er validatie op basis van aanvraagparameters nodig is.
Typische taken zijn onder andere algemene taken met betrekking tot beveiliging, loggen van alle aanvragen, afbeelding/gegevenscompressie en tekencodering, en het aanpassen van ServletRequest.
Wat is een interceptor?
Een interceptor biedt de mogelijkheid om aanvragen en antwoorden te raadplegen of te bewerken vóór en nadat de dispatcher-servlet een controller aanroept, en werkt op Spring-containerniveau.
Wanneer wordt een interceptor gebruikt?
Interceptors kunnen worden gebruikt om taken uit te voeren die globaal moeten worden verwerkt met betrekking tot clientverzoeken. Of wanneer er validatie nodig is waarbij servicelogica wordt aangeroepen.
Typische taken zijn onder andere algemene taken zoals authenticatie/autorisatie, loggen van API-aanroepen en het verwerken van gegevens die naar de controller worden doorgegeven.
Wat is het verschil tussen een filter en een interceptor?
Filters worden uitgevoerd op containerniveau van de servlet, terwijl interceptors worden uitgevoerd op Spring-containerniveau.
Filters kunnen de dispatcher-servlet vóór en na verwerken, terwijl interceptors de controller vóór en na verwerken.
Daarom is het raadzaam om filters te gebruiken voor taken die onafhankelijk van Spring globaal moeten worden verwerkt, en interceptors voor taken die globaal moeten worden verwerkt met betrekking tot clientverzoeken.
Wat is Argument Resolver?
Argument Resolver helpt indirect bij het maken van het gewenste object uit de waarde van een aanvraag wanneer er een aanvraag bij een controller binnenkomt.
Wanneer wordt Argument Resolver gebruikt?
Het kan worden gebruikt wanneer er een aanvraag met een JWT-token binnenkomt. Het token wordt gecontroleerd op geldigheid, waarna de id die is opgeslagen in het token wordt opgehaald en wordt omgezet naar een LoginMember-object.
Wat is het verschil tussen een interceptor en Argument Resolver?
Argument Resolver retourneert het gewenste object uit de waarde van een aanvraag wanneer er een aanvraag bij een controller binnenkomt. Interceptors kunnen geen objecten retourneren. Argument Resolver wordt uitgevoerd nadat de interceptor is uitgevoerd.
Reacties0