FAUXJSP ist eine JSP -Implementierung von Java Server Pages (JSP) zur Verwendung während der Entwicklung: JSPs werden träge interpretiert (anstelle von kompiliert), wodurch die Anwendungs- und Seitenstartzeiten reduziert werden, beschleunigt die Seite, wenn sich JSPS ändert, und es erfordert keine Server -Neustarts. Am besten bei der Entwicklung verwendet, kann auch in der Produktion verwendet werden, wenn die Einhaltung von Spezifikationen nicht kritisch ist.
web.xml:
< servlet >
< servlet-name >FauxJsp</ servlet-name >
< servlet-class >fauxjsp.servlet.JspServlet</ servlet-class >
</ servlet >
< servlet-mapping >
< servlet-name >FauxJsp</ servlet-name >
< url-pattern >*.jsp</ url-pattern >
</ servlet-mapping >Versionen unten (und einschließlich) 1.2.3 sind in Maven Central:
pom.xml:
< dependency >
< groupId >com.github.ggeorgovassilis</ groupId >
< artifactId >fauxjsp</ artifactId >
< version >1.2.3</ version >
</ dependency >Versionen nach 1.2.3 erfordern ein Repository:
< repositories >
< repository >
< id >fauxjsp-repo</ id >
< url >https://github.com/ggeorgovassilis/fauxjsp/raw/gh-pages/</ url >
< snapshots >
< enabled >true</ enabled >
< updatePolicy >always</ updatePolicy >
</ snapshots >
</ repository >
</ repositories >1.2.7-Snapshot (nicht auf Maven Central freigegeben)
1.2.3
1.2.2
1.2.1
1.2.0
1.1.0
1.0.0
trimDirectiveWhiteSpaces , c:set -Körpergehalt implementiert0,0,9
0,0,5-Snapshot
0,0,4-Snapshot
Ja. Zusamenfassend:
Für die meisten von Ihnen ist coole Typen, JSP, schrecklich aus der Mode, aber ich mag es, es für Prototyping und Tagfiles zu verwenden. Leider und überraschend wissen nicht viele Menschen über Tagfiles, obwohl sie eine gut unterstützte und reife Technik zum Erstellen wiederverwendbarer Web-UI-Komponenten sind.
Das Starten einer JSP-Heavy-Anwendung ist langsam, da andere JSP-Implementierungen zuerst JSP und Tagfiles zum Java-Quellcode, dann zum Byte-Code und dann zum Maschinencode kompilieren. Wenn Änderungen an JSP -Dateien vorgenommen werden, muss der gesamte Vorgang wiederholt werden, was die Entwicklung verlangsamt. Irgendwann werden Sie sogar unerklärliche Kompilierfehler, Klassenladenfehler, den Speicher und die derartigeren dergleichen erhalten, Sie wissen, dass Sie genug hatten, und Sie werden den Servlet -Container neu starten.
FAUXJSP implementiert einen JSP -Interpreter und ein JSP -Servlet, das JSP -Dateien liest und im laufenden Fliegen interpretiert und die Kompilierung insgesamt überspringt. Dies bringt den Nutzen von Instant -Seite -Nachladen, schnellen Anwendungszeiten und Robustheit (kein Klassenloader -Fummeln!) Aber offensichtlich sind die generierten JSP -Seiten unter der Last langsamer als die Standardimplementierung, die möglicherweise ein Problem in der Produktion sein kann.
Derzeit implementierte Funktionen:
Einschränkungen und fehlende Funktionen:
c:out funktionieren, aber Taglibs von Drittanbietern wie DisplayTag nicht, es sei denn, Sie implementieren sie für FauxJSP erneut.classpath: Präfix zum Auflösen von Tagfiles und JSPs im Klassenpfad. Unterstützt nicht die Standardmethode zur Lösung von Klassenpfadressourcen.Weil:
Bonus:
< dependency >
< groupId >com.github.ggeorgovassilis</ groupId >
< artifactId >fauxjsp</ artifactId >
< version >1.1.0</ version >
</ dependency >ODER
Quellen herunterladen und kompilieren
git clone https://github.com/ggeorgovassilis/fauxjsp.git
cd fauxjsp
mvn install< servlet >
< servlet-name >FauxJsp</ servlet-name >
< servlet-class >fauxjsp.servlet.JspServlet</ servlet-class >
<!-- optionally specify a root for resource lookup, defaults to "/"
<init-param>
<param-name>base-path</param-name>
<param-value>/WEB-INF/jsp/</param-value>
</init-param>
-->
</ servlet >
< servlet-mapping >
< servlet-name >FauxJsp</ servlet-name >
< url-pattern >*.jsp</ url-pattern >
</ servlet-mapping > Servlet API, JSTL, EL werden wie provided , da der Servlet -Container oder die Webanwendung diese Abhängigkeiten beitragen
log4j, Beanshell werden wie provided weil sie optional sind
commons-Lang ist als compile abgebildet, weil es obligatorisch ist
Weitere Details finden Sie im POM.
Bitte senden Sie einen Fehlerbericht, wenn Sie einen Fehler finden oder eine implementierte Funktion benötigen. Jetzt, im realen (Projekt-) Leben, haben Sie wahrscheinlich einen engen Zeitplan und möchten nicht auf eine offizielle Lösung warten. FauxJSP ist modular und leicht erweiterbar. Schauen Sie sich also das nächste Kapitel über die Architektur von FauxJSP an, mit dem Sie die verschiedenen, eher einfachen Komponenten verstehen und neue Funktionen implementieren können.
JspServlet akzeptiert eine HTTP -Anfrage und macht den angeforderten JSP. Die gesamte Sequenz sieht so aus:
ServletRequest abjspbase (siehe Javadocs für JspServlet ) für die JSP -Datei anJspParserFactory für einen neuen JspParserJspParser , der sie analysiert, rekursiv Abhängigkeiten auflöst und ein JspPage zurückgibtRenderSessionJspRendererFactory für einen neuen JspRendererJspPage JspRenderer der es RenderSession JspServlet verfügt über eine Reihe geschützter Methoden, die die zuvor genannten Fabriken konstruieren. Wenn Sie spezielle Setups benötigen, können Sie diese Konstruktormethoden überschreiben, damit Sie Ihre eigenen Fabriken angeben können, die geänderte oder vollständig neue Implementierungen von Parsers und Renderern zurückgeben können.
Der JspParser und insbesondere seine einzige Implementierung JspParserImpl erhält einen JSP -Dateispeicherort, rendert es und gibt die analysierten Ergebnisse zurück. Ausführlich:
JspParser.parse(path) erhält den Pfad der JSP -Datei zum RendernResourceResolver -Instanz (die JspParserFactory legt diese auf), die die JSP -Datei als Zeichenfolge zurückgibt.JspNode s.TagLibDefinitionCache eingebaut, das sicherstellt, dass Taglibs während jeder Anforderung nur einmal gelesen werden.JspParserFactory für einen neuen Parser aufgefordert, der das Tagfile rekursiv analysiert. Leider ist es derzeit nicht möglich, Taglibs als Tagfiles zu laden. Es ist jedoch möglich, fehlende Taglibs zu verwenden, indem es eine spezielle Implementierung für FauxJSP selbst bereitstellt. Abhängig vom Taglib versuchen Sie zu simulieren, dass dies eine arbeitsintensive Aufgabe ist oder nicht. In einigen Beispielen schauen Sie sich die JstlCoreTaglib* -Klassen an. Die Standard -Fabrik DefaultJspParserFactoryImpl stellt diejenigen unter einem speziellen Namespace ein, einer für jede Taglib -Methode.
<%@ taglib prefix uri tagdir %>
<@ include file %>
<%@ attribute name required rtexprvalue type %>
< jsp : attribute name = " ... " >...</ jsp : attribute >
< jsp : body >...</ jsp : body >
< jsp : doBody />< c : out value = " ... " />
< c : choose test = " ... " >...</ c : choose >
< c : when test = " ... " >...</ c : when >
< c : otherwise >...</ c : otherwise >
< c : forEach var = " ... " items = " ... " varStatus = " ... " begin = " ... " end = " ... " >...</ c : forEach >
< c : if test = " ... " >...</ c : if >
< c : set var = " ... " value = " ... " />
< fmt : message key = " ... " />
< fmt : setBundle basename = " ... " />
< fmt : formatNumber value = " ... " .../>
< fmt : formatDate value = " ... " .../>
< fmt : setLocale value = " ... " />
FAUXJSP delegiert an die vom Anwendungsserver verwendete Standard -JSTL -Funktionsinimpomentierung, sodass alles über die Box funktioniert.
Wenn Sie mehr Funktionstennzeichen benötigen, vergessen Sie nicht, sie in Web.xml zu deklarieren:
< jsp-config >
< taglib >
< taglib-uri >http://java.sun.com/jstl/core-rt</ taglib-uri >
< taglib-location >META-INF/c-1_0-rt.tld</ taglib-location >
</ taglib >
</ jsp-config >Taglib-Location kann ein Server- oder ClassPath-Ressourcenpfad sein.
Wie bereits geschrieben, kann FauxJSP Taglibs nicht verwenden und muss sie stattdessen nachahmen, was bedeutet, dass jemand diese Emulation programmieren muss.
Schritt 1 : Erstellen Sie die Taglib -Implementierung. Finden Sie einfach eines der bereits simulierten Taglibs wie jstlCoretaglibout und kopieren Sie es und fügen Sie es ein
public class TaglibAdd extends TaglibDefinition {
protected void runAdd ( RenderSession session , JspTaglibInvocation invocation ) {
String xExpression = invocation . getArguments (). get ( "x" );
if ( xExpression == null )
throw new RuntimeException ( "Missing x argument" );
Object x = session . elEvaluation . evaluate ( xExpression , session );
String yExpression = invocation . getArguments (). get ( "y" );
if ( yExpression == null )
throw new RuntimeException ( "Missing y argument" );
Object y = session . elEvaluation . evaluate ( yExpression , session );
try {
int ix = ( Number ) x ;
int iy = ( Number ) y ;
String s = "" +( ix + iy );
session . response . getOutputStream (). write (( s ). getBytes ( session . response . getCharacterEncoding ()));
} catch ( Exception e ) {
throw new JspRenderException ( invocation , e );
}
}
@ Override
public void render ( RenderSession session , JspTaglibInvocation invocation ) {
runAdd ( session , invocation );
}
public TaglibAdd () {
this . name = "add" ;
this . attributes . put ( "x" , new AttributeDefinition ( "x" , Integer . class . getName (), true , true ));
this . attributes . put ( "y" , new AttributeDefinition ( "y" , Integer . class . getName (), true , true ));
}
}
Schritt 2 : Erweitern Sie defaultJspparSerFactoryImpl und überschreiben Sie die setup -Methode. Hier können Sie den neuen Taglib registrieren, den Sie geschrieben haben
public class MyJspParserFactory extends DefaultJspParserFactoryImpl {
protected void setup ( JspParserImpl parser ) {
super . setup ( parser );
parser . registerTaglibDefinition (
"http://mytaglibs/add" ,
new TaglibAdd ());
}
} Schritt 3 : Erweitern Sie JSPServlet und getJspParserFactory
public class MyJspServlet extends JspServlet {
protected JspParserFactory getJspParserFactory ( ServletConfig config ){
ResourceResolver location = new ServletResourceResolver ( jspBase , getServletContext ());
DefaultJspParserFactoryImpl factory = new MyJspParserFactory ( location );
return factory ;
}
}Schritt 4 : Verwenden Sie Ihre neue JSPServlet -Implementierung in web.xml anstelle des alten JSPServlet
< servlet >
< servlet-name >FauxJsp</ servlet-name >
< servlet-class >MyJspServlet</ servlet-class >
</ servlet >
< servlet-mapping >
< servlet-name >FauxJsp</ servlet-name >
< url-pattern >*.jsp</ url-pattern >
</ servlet-mapping > JspServlet loget sich über log4j ab, falls sich auf dem Klassenpfad befindet, andernfalls über den Standard -JDK -Protokollierungsmechanismus. Ein mögliches Protokollierungs -Setup in log4j.properties könnte so aussehen:
log4j.rootLogger=INFO, stdout
log4j.logger.fauxjsp=INFO, stdout
log4j.additivity.fauxjsp.impl.parser.JspParserImpl=false
log4j.appender.stdout=org.apache.log4j.ConsoleAppender
log4j.appender.stdout.Target=System.out
log4j.appender.stdout.layout=org.apache.log4j.PatternLayout
log4j.appender.stdout.layout.ConversionPattern=%d{yyyy-MM-dd HH:mm:ss} %-5p %c{1}:%L - %m%n
Skriptlets werden unter Verwendung von Beanshell implementiert, daher sind einige Abweichungen vom Standard -Skriptlet -Verhalten zu erwarten. Die Drehbücher werden nicht aktiviert, es sei denn, der Beanshell -Interpreter befindet sich auf dem Klassenpfad. Aktuelle Einschränkungen sind:
Idealerweise finden Sie einen Weg, der sowohl in der Produktion JSP -Umgebung als auch mit FauxJSP funktioniert. Ein Beispiel wäre der Fall von Varargs, die in Skriptlets verwendet wurden, über die wir zuvor gesprochen haben. Der FAUXJSP -Parser wird wahrscheinlich durch Zeichenfolgen verwirrt, die in EL -Ausdrücken und -Skriptlets erscheinen, die an anderer Stelle als Grenzwerte wie <,>, {,} usw. verwendet werden. In diesem Fall versuchen Sie, Escapes wie U007B für {.
Der Anwendungsfall ist, dass Ihre Tagfiles oder JSPs auf andere Tagfiles oder JSPs verweisen, die sich im Klassenpfad befinden (z. B. eine JAR -Datei). Verwenden Sie tagdir nicht, sondern verwenden Sie stattdessen uri wenn Sie die Ressource, z. B. die Ressource, einbeziehen:
<%@ taglib prefix = " cp " uri = " classpath:/tagfiles " %> Sie haben wahrscheinlich festgestellt, dass die JstlView und InternalViewResolver nicht funktionieren und der Frühling Ihre JSPs nicht findet. Unter der Motorhaube sollte der Spring das Modell (das M in MVC) in die HttpServletRequest -Attribute einbringen und die Anfrage an FAUXJSP weiterleiten, dies jedoch nicht. Wir können einen einfachen Weiterleitungsmechanismus wie SO implementieren:
import java . util . Locale ;
import org . springframework . stereotype . Component ;
import org . springframework . web . servlet . View ;
import org . springframework . web . servlet . ViewResolver ;
@ Component
public class ForwardingViewResolver implements ViewResolver {
@ Override
public View resolveViewName ( String viewName , Locale locale ) throws Exception {
ForwardingView view = new ForwardingView ();
view . setUrl ( "classpath:/jsp/" + viewName + ".jsp" );
return view ;
}
} import java . util . Map ;
import javax . servlet . RequestDispatcher ;
import javax . servlet . http . HttpServletRequest ;
import javax . servlet . http . HttpServletRequestWrapper ;
import javax . servlet . http . HttpServletResponse ;
import org . springframework . web . servlet . view . InternalResourceView ;
public class ForwardingView extends InternalResourceView {
@ SuppressWarnings ( "unchecked" )
@ Override
public void render ( Map < String , ?> model , HttpServletRequest request , HttpServletResponse response )
throws Exception {
HttpServletRequestWrapper wrapper = new HttpServletRequestWrapper ( request ) {
@ Override
public String getServletPath () {
return getUrl ();
}
};
exposeModelAsRequestAttributes (( Map < String , Object >) model , wrapper );
exposeHelpers ( wrapper );
RequestDispatcher rd = request . getServletContext (). getNamedDispatcher ( "FauxJsp" );
rd . forward ( wrapper , response );
}
}Das einfache Vorhandensein dieser beiden Komponenten im Webanwendungskontext sollte ausreichen, damit sie aufgegriffen und aktiviert werden.
JspServlet kann so konfiguriert werden, dass JSPs analysiert werden. Dies ist eine geringfügige Leistungsverbesserung, da normalerweise das Rendern langsamer ist als das Parsen.
< servlet >
< servlet-name >FauxJsp</ servlet-name >
< servlet-class >fauxjsp.servlet.JspServlet</ servlet-class >
< init-param >
< param-name >cachePages</ param-name >
< param-value >true</ param-value >
</ init-param >
</ servlet > Geben Sie ein Servlet Init Parameter trimDirectiveWhiteSpaces
< servlet >
< servlet-name >FauxJsp</ servlet-name >
< servlet-class >fauxjsp.servlet.JspServlet</ servlet-class >
< init-param >
< param-name >trimDirectiveWhiteSpaces</ param-name >
< param-value >true</ param-value >
</ init-param >
</ servlet > Merkmale kommen in der Nähe Irgendwann in der Zukunft:
Science -Fiction (Dinge, die ich eine grobe Idee habe, wie man implementiert, muss aber noch trainieren und vielleicht nie kommen):
Ross Studtman für JSP -Tutorials, die viele großartige Unit -Tests inspirierten.
FauxJSP ist unter der GPL erhältlich. Da FauxJSP ein Entwicklungstool ist, würden Sie es normalerweise nicht mit Ihren Anwendungsbinärdateien in Produktion einsetzen, sodass der "nichtkommerzielle" Aspekt der GPL keine Auswirkungen auf Ihre Anwendung.