[JAVA] [Vérification de comparaison] Quelle est la différence entre la productivité du développement de l'application Spring Boot et celle du passé?

** Quelle est la différence entre la productivité du développement des applications basées sur Spring Boot et celle du développement des applications Web héritées? ** **

Avec une application web "EasyBuggy" basée sur une petite technologie ancienne et son clone (exactement la même fonction) Comparez un ["Easy Buggy Boot"] basé sur Spring Boot (https://github.com/k-tamura/easybuggy4sb/blob/master/README.jp.md) avec les chiffres suivants qui affectent la productivité du développement: Je l'ai essayé.

--Temps de construction

Différences de configuration

À propos, les principales différences de configuration sont les suivantes.

Différence EasyBuggy EasyBuggy Boot
Technologie de base Servlet 3.0.1 Spring Boot 1.5.6 (Servlet 3.0.1)
Couche de présentation inutilisé(Certains JSP 2.2 + JSTL 1.2) Thymeleaf 2.1.5 (Certains JSP 2.3 + JSTL 1.2)
Conteneur Java Apache Tomcat/7.0.37 Apache Tomcat/8.5.16
Client DB/serveur JDBC / Derby 10.8.3.0 Spring JDBC 4.3.9 / Derby 10.12.1.1 (Pour Java 7), Ou 10.13.1.1 (Pour Java 8)
Client LDAP/serveur Apache DS Client API 1.0.0 / Server 1.5.5 Spring LDAP 2.3.1 / unboundid-ldapsdk 3.2.1
Email JavaMail 1.5.1 JavaMail 1.5.1 (Java Mail introduit par Spring Boot Mail 1.5.Remplacer 6)
Outils de développement Aucun Spring Boot Developer Tools 1.5.6
Java Prend en charge Java 6 et supérieur Prend en charge Java 7 et supérieur

Il est temps de construire

Tout d'abord, le temps de construction moyen. Le résultat est le suivant.

EasyBuggy

Environ 6 secondes

$ mvn package
[INFO] Scanning for projects...
[INFO]                                                                         
[INFO] ------------------------------------------------------------------------
[INFO] Building easybuggy 1-SNAPSHOT
[INFO] ------------------------------------------------------------------------

・ ・ ・(Omis parce que c'est long)・ ・ ・

[INFO] --- tomcat7-maven-plugin:2.1:exec-war-only (tomcat-run) @ easybuggy ---
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 5.847s
[INFO] Finished at: Thu Aug 31 23:28:55 JST 2017
[INFO] Final Memory: 36M/220M
[INFO] ------------------------------------------------------------------------

EasyBuggy Boot

Environ 12 secondes

$ mvn package
[INFO] Scanning for projects...
[INFO]                                                                         
[INFO] ------------------------------------------------------------------------
[INFO] Building easybuggy4sb 1.0.0-SNAPSHOT
[INFO] ------------------------------------------------------------------------
[INFO] 

・ ・ ・(Omis parce que c'est long)・ ・ ・

[INFO] --- spring-boot-maven-plugin:1.5.6.RELEASE:repackage (default) @ easybuggy4sb ---
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 12.448s
[INFO] Finished at: Thu Aug 31 23:26:55 JST 2017
[INFO] Final Memory: 26M/242M
[INFO] ------------------------------------------------------------------------

Le premier est plus rapide de plus du double de la différence.

À propos, l'environnement utilisé pour la vérification est CentOS 6.9 sur VMWare, CPU 4 cœurs (Intel® Xeon® X5680 @ 3,33 GHz) et mémoire 4 Go. Toutes les bibliothèques dépendantes ont été téléchargées localement.

Le temps de démarrage

Le temps de démarrage moyen est le suivant.

EasyBuggy

Environ 3 secondes

$ java -jar easybuggy.jar
8 31, 2017 2:44:56 pm org.apache.coyote.AbstractProtocol init
information: Initializing ProtocolHandler ["http-bio-8080"]
8 31, 2017 2:44:56 pm org.apache.catalina.core.StandardService startInternal
information: Starting service Tomcat
8 31, 2017 2:44:56 pm org.apache.catalina.core.StandardEngine startInternal
information: Starting Servlet Engine: Apache Tomcat/7.0.37
8 31, 2017 2:44:59 pm org.apache.coyote.AbstractProtocol start
information: Starting ProtocolHandler ["http-bio-8080"]

EasyBuggy Boot

Environ 15 secondes (environ 9 secondes pour mvn spring-boot: run)

$ java -jar ROOT.war
SLF4J: Class path contains multiple SLF4J bindings.
SLF4J: Found binding in [jar:file:/C:/Users/ktamura/git/easybuggy4sb/target/ROOT.war!/WEB-INF/lib/logback-classic-1.1.11.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: Found binding in [jar:file:/C:/Users/ktamura/git/easybuggy4sb/target/ROOT.war!/WEB-INF/lib/slf4j-log4j12-1.7.25.jar!/org/slf4j/impl/StaticLoggerBinder.class]
SLF4J: See http://www.slf4j.org/codes.html#multiple_bindings for an explanation.
SLF4J: Actual binding is of type [ch.qos.logback.classic.util.ContextSelectorStaticBinder]

  .   ____          _            __ _ _
 /\\ / ___'_ __ _ _(_)_ __  __ _ \ \ \ \
( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
 \\/  ___)| |_)| | | | | || (_| |  ) ) ) )
  '  |____| .__|_| |_|_| |_\__, | / / / /
 =========|_|==============|___/=/_/_/_/
 :: Spring Boot ::        (v1.5.6.RELEASE)
2017-08-31 15:08:46.454  INFO 5460 --- [           main] o.t.e.Easybuggy4sbApplication            : Starting Easybuggy4sbApplication v1.0.0-SNAPSHOT on ktamura-PC with PID 5460 (C:\Users\ktamura\git\easybuggy4sb\target\ROOT.war started by k
tamura in C:\Users\ktamura\git\easybuggy4sb)

・ ・ ・(Omis parce que c'est long)・ ・ ・

2017-08-31 15:09:01.198  INFO 5460 --- [           main] o.s.c.support.DefaultLifecycleProcessor  : Starting beans in phase 0
2017-08-31 15:09:01.273  INFO 5460 --- [           main] s.b.c.e.t.TomcatEmbeddedServletContainer : Tomcat started on port(s): 8080 (http)
2017-08-31 15:09:01.276  INFO 5460 --- [           main] o.t.e.Easybuggy4sbApplication            : Started Easybuggy4sbApplication in 15.253 seconds (JVM running for 15.81)

EasyBuggy démarre très rapidement, il semble donc lent même en 15 secondes. En regardant le journal EasyBuggy Boot, il n'y a pas beaucoup de temps de traitement, donc il n'y a pas beaucoup de place pour l'amélioration. Je pense que le temps de démarrage de Spring Boot prendra au moins autant.

Ce résultat est le résultat du Tomcat intégré, mais le résultat est presque le même même lorsque le fichier de guerre est déployé sur le Tomcat non intégré.

Cependant, EasyBuggy Boot prend environ 9 secondes lorsqu'il est démarré avec la commande mvn spring-boot: run. J'ai comparé les journaux des deux pour voir pourquoi cette différence se produit, mais il semble qu'il n'y ait pas de grande différence dans le traitement en cours d'exécution, et je n'en connaissais pas la raison claire.

Temps entre la modification du code source et la confirmation de l'opération

Le temps moyen entre la modification du code source et la possibilité de vérifier l'opération est le suivant.

EasyBuggy

Environ 15 secondes

EasyBuggy utilise la commande mvn install pour créer un fichier jar et tout démarrer en même temps. Il faut environ 15 secondes pour redémarrer, y compris le temps nécessaire pour cela et l'arrêt. Bien sûr, cela ne prend pas beaucoup de temps en développement réel car il reflète la correction lors du débogage avec le hot swap de JVM ... (Ce sera plus rapide si JRebel est introduit).

EasyBuggy Boot

Environ 3 secondes

2017-09-01 12:04:55.414  INFO 2800 --- [     Thread-104] ationConfigEmbeddedWebApplicationContext : Closing org.springframework.boot.context.embedded.AnnotationConfigEmbeddedWebApplicationContext@27231264: startup date [Fri Sep 01 12:04:21 JST 2017]; root of context hierarchy
2017-09-01 12:04:55.417  INFO 2800 --- [     Thread-104] ationConfigEmbeddedWebApplicationContext : Closing org.springframework.boot.context.embedded.AnnotationConfigEmbeddedWebApplicationContext@4274ec33: startup date [Fri Sep 01 12:04:23 JST 2017]; parent: org.springframework.boot.context.embedded.AnnotationConfigEmbeddedWebApplicationContext@27231264
2017-09-01 12:04:55.532  INFO 2800 --- [     Thread-104] o.s.c.support.DefaultLifecycleProcessor  : Stopping beans in phase 0
2017-09-01 12:04:55.537  WARN 2800 --- [     Thread-104] o.s.b.f.support.DisposableBeanAdapter    : Invocation of destroy method failed on bean with name 'inMemoryDatabaseShutdownExecutor': java.sql.SQLSyntaxErrorException: Syntax error: Encountered "SHUTDOWN" at line 1, column 1.
2017-09-01 12:04:55.538  INFO 2800 --- [     Thread-104] o.s.j.e.a.AnnotationMBeanExporter        : Unregistering JMX-exposed beans on shutdown

  .   ____          _            __ _ _
 /\\ / ___'_ __ _ _(_)_ __  __ _ \ \ \ \
( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
 \\/  ___)| |_)| | | | | || (_| |  ) ) ) )
  '  |____| .__|_| |_|_| |_\__, | / / / /
 =========|_|==============|___/=/_/_/_/
 :: Spring Boot ::        (v1.5.6.RELEASE)

・ ・ ・(Omis parce que c'est long)・ ・ ・

2017-09-01 12:04:57.895  INFO 2800 --- [  restartedMain] s.b.c.e.t.TomcatEmbeddedServletContainer : Tomcat started on port(s): 8081 (http)
2017-09-01 12:04:57.897  INFO 2800 --- [  restartedMain] o.s.c.support.DefaultLifecycleProcessor  : Starting beans in phase 0
2017-09-01 12:04:57.923  INFO 2800 --- [  restartedMain] s.b.c.e.t.TomcatEmbeddedServletContainer : Tomcat started on port(s): 8080 (http)
2017-09-01 12:04:57.925  INFO 2800 --- [  restartedMain] o.t.e.Easybuggy4sbApplication            : Started Easybuggy4sbApplication in 2.125 seconds (JVM running for 828.681)

EasyBuggy Boot a introduit Spring Boot Developer Tools 1.5.6, de sorte que les correctifs sont immédiatement reflétés et vous pouvez développer presque sans attendre. Cette sensation de vitesse est très confortable.

Nombre de lignes de code source

Comparons le nombre de lignes de code source.

EasyBuggy

Type Ligne vide Ligne de commentaire code Nombre de fichiers
Java 838 359 4881 98
JSP 11 10 810 6
XML 5 0 47 2
HTML 2 0 35 7
properties 71 325 799 6
Total 927 694 6572 119

EasyBuggy Boot

Type Ligne vide Ligne de commentaire code Nombre de fichiers
Java 663 131 3500 92
HTML 8 39 1034 46
JSP 0 4 149 2
XML 0 1 32 4
SQL 0 0 18 3
JSON 0 0 17 1
DTD 0 0 3 1
LDIF 0 5 46 1
properties 86 321 830 4
Total 757 501 5629 154

Le nombre de lignes de code source d'EasyBuggy est de 6 572, tandis qu'EasyBuggy Boot est de 5 629, donc l'utilisation de Spring Boot peut réduire le nombre d'environ 15%. Il y a une différence d'environ 1,3 fois dans le nombre de fichiers, mais je pense que c'est parce qu'EasyBuggy n'a pas séparé l'écran et la logique en fichiers séparés (JSP, etc.) (* Je voulais expliquer un bogue dans un fichier, donc je l'ai fait comme ça J'ai fait).

[Bonus] Lisibilité du code source

Comment la lisibilité du code source a-t-elle changé? Pour les fonctions suivantes

xsspage.png

Le code source de chacun est le suivant.

EasyBuggy

XSSServlet.java


package org.t246osslab.easybuggy.vulnerabilities;

import java.io.IOException;
import java.util.Locale;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.t246osslab.easybuggy.core.utils.HTTPResponseCreator;
import org.t246osslab.easybuggy.core.utils.MessageUtils;

@SuppressWarnings("serial")
@WebServlet(urlPatterns = { "/xss" })
public class XSSServlet extends HttpServlet {

    private static final Logger log = LoggerFactory.getLogger(XSSServlet.class);

    @Override
    protected void service(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException {

        String string = req.getParameter("string");
        Locale locale = req.getLocale();

        StringBuilder bodyHtml = new StringBuilder();

        bodyHtml.append("<form action=\"xss\" method=\"post\">");
        bodyHtml.append(MessageUtils.getMsg("description.reverse.string", locale));
        bodyHtml.append("<br><br>");
        bodyHtml.append(MessageUtils.getMsg("label.string", locale) + ": ");
        bodyHtml.append("<input type=\"text\" name=\"string\" size=\"100\" maxlength=\"100\">");
        bodyHtml.append("<br><br>");
        bodyHtml.append("<input type=\"submit\" value=\"" + MessageUtils.getMsg("label.submit", locale) + "\">");
        bodyHtml.append("<br><br>");

        if (!StringUtils.isBlank(string)) {
            // Reverse the given string
            String reversedName = StringUtils.reverse(string);
            bodyHtml.append(MessageUtils.getMsg("label.reversed.string", locale) + " : "
                + reversedName);
        } else {
            bodyHtml.append(MessageUtils.getMsg("msg.enter.string", locale));
        }
        bodyHtml.append("<br><br>");
        bodyHtml.append(MessageUtils.getInfoMsg("msg.note.xss", locale));
        bodyHtml.append("</form>");

        HTTPResponseCreator.createSimpleResponse(req, res, MessageUtils.getMsg("title.xss.page", locale),
                bodyHtml.toString());
    }
}

EasyBuggy Boot

xss.html


<!DOCTYPE html SYSTEM "http://www.thymeleaf.org/dtd/xhtml1-strict-thymeleaf-spring4-4.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:th="http://www.thymeleaf.org" th:with="lang=${#locale.language}" th:lang="${lang}">
<div th:replace="head"></div>
<body style="margin-left: 20px; margin-right: 20px;">
	<div th:replace="header"></div>
	<form action="xss" method="post">
		<p th:text="#{description.reverse.string}" /><br />
		<label th:text="#{label.string}"></label><span>: </span>
			<input type="text" name="string" size="100" maxlength="100" /><br /><br /> 
			<input type="submit" /><br /><br />
			<p th:utext="${msg}" /><br />
		<div class="alert alert-info" role="alert">
			<span class="glyphicon glyphicon-info-sign" th:utext="#{msg.note.xss}"></span>
		</div>
	</form>
</body>
</html>

XSSController.java


package org.t246osslab.easybuggy4sb.vulnerabilities;

import java.util.Locale;

import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.MessageSource;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.servlet.ModelAndView;

@Controller
public class XSSController {

    @Autowired
    MessageSource msg;

    @RequestMapping(value = "/xss")
    public ModelAndView process(@RequestParam(value = "string", required = false) String string, ModelAndView mav,
            Locale locale) {
        mav.setViewName("xss");
        mav.addObject("title", msg.getMessage("title.xss.page", null, locale));
        if (!StringUtils.isBlank(string)) {
            // Reverse the given string
            String reversedName = StringUtils.reverse(string);
            mav.addObject("msg", msg.getMessage("label.reversed.string", null, locale) + " : " + reversedName);
        } else {
            mav.addObject("msg", msg.getMessage("msg.enter.string", null, locale));
        }
        return mav;
    }
}

Comme la fonction elle-même est simple, il peut ne pas y avoir de grande différence de lisibilité, mais cette dernière est plus facile à répartir le travail entre le programmeur et le concepteur. Bien sûr, si vous utilisez JSP, le premier sera proche de cela.

Recommended Posts

[Vérification de comparaison] Quelle est la différence entre la productivité du développement de l'application Spring Boot et celle du passé?
[Vérification] Comparaison de la vitesse de démarrage de Spring Boot et de Micronaut
L'histoire de la montée de Spring Boot de la série 1.5 à la série 2.1 part2
[Swift] La couleur de NavigationBar est différente (plus claire) de la couleur spécifiée.
[Spring Boot] J'ai étudié comment implémenter le post-traitement de la demande reçue.
Comment définir des variables d'environnement dans le fichier de propriétés de l'application Spring Boot
Ce qui est différent du langage PHP. [Remarque]
L'histoire de la montée de la série Spring Boot 1.5 à la série 2.1
Vérifions la sensation de Spring Boot + Swagger 2.0
Le nom officiel de Spring MVC est Spring Web MVC
[Spring Boot] Comment se référer au fichier de propriétés
Comment écrire Scala du point de vue de Java
La comparaison d'énumération est ==, et equals est bonne [Java]
Accédez au h2db intégré de Spring Boot avec jdbcTemplate
05. J'ai essayé de supprimer la source de Spring Boot
J'ai essayé de réduire la capacité de Spring Boot
Comment utiliser CommandLineRunner dans Spring Batch of Spring Boot
Comment démarrer par environnement avec Spring Boot de Maven
Un record d'étude du Spring Framework à partir de zéro
Comment la valeur suivante de l'objet Time est-elle correcte?