Spring Boot statt JavaEE

Bitte aktiviere JavaScript!
Hallo zusammen,
ich möchte mein Programm umbauen und es zu Microservices mit Spring boot aufbauen. Nun habe ich eine Verständnisfrage: Wenn ich eine View aufbaue, kommuniziert diese dann auch über REST mit den Services?

Möchte nämlich JSF Primefaces nutzen als View, da ich mir da ein Template gekauft habe. Wenn es etwas einfacheres als JSF im Zusammenhang auch gut, dann freue ich mich über Tipps
 
Üblicherweise kommuniziert auch die per Rest mit den anderen Services.

Du kannst da durchaus auch JSF nutzen, häufig nutzt man aber was Client-basiertes.
 
Vaadin zb? JSF hab ich jetzt relativ gut drauf. müsste da wieder von 0 anfangen. das will ich eigentlich vermeiden, es sei denn es ist super einfach :p weiß da grad nicht, wo ich ansetzen soll. Mein erster Service wäre jetzt die View, in welcher Produkte angelegt werden können, die an einen service gehen, der es ihn die DB speichert
 
In der Wahl des Frameworks ist man da nicht eingeschränkt, das ist doch das schöne an dem Ansatz ;)
Vaadin ist möglich, oder React, Vue, Angular, ...
 
Hab null Ahnung von Javascript, will ich auch ehrlich nicht.

Vaadin erinnert mich an Swing, also alles rein in Java -> find ich gut. Aber da muss man so viel CSS machen damit es hübsch ist. In einem anderen Forum habe ich gelesen, dass es ein fix und fertig Theme gibt. Hab es nur noch nicht gefunden, aber das wäre ja gut, wenn es da schon was fertiges geben würde, wo man nur noch die Menüs usw anpassen muss :D Muss funktionieren, schön sein ist unwichtig :D
 
Hab ich auch schon geschaut erst, aber das geht nicht so out of the box. Primefaces React würde gehen oder aber ist das nicht auch JavaScript?
 
jsf und spring boot muss erst irgendwas umkonfiguriert werden, beim 2. versuch ging es immer noch nicht, das ist mir dann zu nervraubend noch weiter rumzubasteln
 
aber dann muss ich das frontend auf nem Aappserver laufen lassen oder? Das Frontend kommuniziert dann über Rest mit den Services?
 
Die Services sollten sowieso per Rest (oder vergleichbarer abstrakter Schnittstelle kommunizieren).

Aber ja, das Frontend müsste dann in einem App-Server laufen. Mit Docker ist das aber nicht mehr Aufwand, als Spring Boot mit embedded Server.
 
Ok, wäre ne Lösung. Danke.

Hast du ne Idee, warum mein Service nicht startet?! Im Eclipse gehts, außerhalb eclipse nicht.
Code:
ERROR org.springframework.boot.SpringApplication - Application run failed
org.springframework.context.ApplicationContextException: Unable to start web server; nested exception is org.springframework.context.ApplicationContextException: Unable to start ServletWebServerApplicationContext due to missing ServletWebServerFactory bean.
       at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.onRefresh(ServletWebServerApplicationContext.java:155)
       at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:544)
       at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:140)
       at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:759)
       at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:395)
       at org.springframework.boot.SpringApplication.run(SpringApplication.java:327)
       at org.springframework.boot.SpringApplication.run(SpringApplication.java:1255)
       at org.springframework.boot.SpringApplication.run(SpringApplication.java:1243)
Caused by: org.springframework.context.ApplicationContextException: Unable to start ServletWebServerApplicationContext due to missing ServletWebServerFactory bean.
 
Irgendwas wird falsch konfiguriert sein...ich könnte jetzt raten, aber das wird wenig hilfreich sein.

Hast du eines der Beispiele als Grundlage genommen?
 
Ja ist ein Beispiel. wie gesagt in Eclipse läuft es. Ich vermute, dass da was nicht gepackt wird oder so?! Vielleicht exportiere ich das auch falsch. Ich klicke auf Export > Runnable Jar und auf dem Server java -jar Blabla.jar

hier meine POM, vielleicht hast du nen Plan

Code:
<?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.example</groupId>
    <artifactId>demo</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <packaging>jar</packaging>

    <name>demo</name>
    <description>Demo project for Spring Boot</description>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.0.2.RELEASE</version>
    </parent>

    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
        <java.version>1.8</java.version>
        <spring-cloud.version>Finchley.BUILD-SNAPSHOT</spring-cloud.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-actuator</artifactId>
        </dependency>
  
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
        </dependency>
        <dependency>
            <groupId>com.fasterxml.jackson.dataformat</groupId>
            <artifactId>jackson-dataformat-xml</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-devtools</artifactId>
            <scope>runtime</scope>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
      
    </dependencies>

    <dependencyManagement>
        <dependencies>
            <dependency>
                <groupId>org.springframework.cloud</groupId>
                <artifactId>spring-cloud-dependencies</artifactId>
                <version>${spring-cloud.version}</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>
        </dependencies>
    </dependencyManagement>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>

    <repositories>
        <repository>
            <id>spring-snapshots</id>
            <name>Spring Snapshots</name>
            <url>https://repo.spring.io/snapshot</url>
            <snapshots>
                <enabled>true</enabled>
            </snapshots>
        </repository>
        <repository>
            <id>spring-milestones</id>
            <name>Spring Milestones</name>
            <url>https://repo.spring.io/milestone</url>
            <snapshots>
                <enabled>false</enabled>
            </snapshots>
        </repository>
    </repositories>


</project>
 
Oh guter Tipp, danke! Lokal Ging es schon mal außerhalb Eclipse, nun lad ich es mal auf den Server... da gleich noch ne Frage, jeder Microservice ist 30 MB groß. Die ganzen Libarys kann man doch sicher irgendwo einmal bereitstellen und nicht für jeden Service doppelt und dreifach oder?
 
naja, wenn man geteilte Libraries nutzt, binden man die Services wieder aneinander und verliert damit wieder einen der Vorteile
 
ah ok, ja das stimmt natürlich. Also nur die nötigen Libs rein um Speicher zu sparen.
Mit dem Mavenbuilt hat geklappt! Vielen vielen Dank. Wäre ich in 10 Jahren noch nicht drauf gekommen.

Hast du noch einen Tipp, wie man die Services deployed? Ich würde die jetzt einfach (wie soeben) alle auf den Server in einen Ordner packen (fachlich sortiert) und vielleicht noch mit init.d startbar machen.

Jetzt habe ich den service mit java -jar service.jar gestartet. Nach dem Schließen des SSH Fensters, ist der Service down. Wir macht mans richtig?o_O
 
Ok, der Kostet aber :D hab grad mal 3 services auf dem Testserver gestartet, das ganze sah dann so aus und die Kiste ist herunter gefahren... 2GB RAM. Die Services machen NICHTS außer da sein

Kann oder muss man den RAM Speicher pro Service begrenzen?
 

Anhänge

danke dir, hab grad mal mit -xmx gestartet, das passt :) Muss nur schauen wie ich den bedarf eines jeden services erfahre, any idea?
 
dacht ich mir :D jetzt muss ich nur noch herausbekommen, wie ich einen service als neue Instanz clone. die bekommt ja sicher einen neuen port oder? hast du Coach da einen tipp wonach ich suchen muss?
 
Warum klonen?
Einfach eine neue Instanz mit zufälligem Port starten (afaik passiert das, wenn man Port 0 nutzt). Die meldet sich beim Eureka-Server (nutzt du doch, oder vertu ich mich da grad?) und wird darüber gefunden/findet darüber alles
 
äää echt? So einfach?? Also kann ich das
server.port=8761

in jedem service weglassen? ich nutze Eureka genau und ein API Gateway, was das Routing zum richtigen port übernimmt (hoffe ich)
 
Jap, genau dafür ist Eureka da.
Das Gateway (Zuul?) nutzt ja auch Eureka, würde ich aber nicht für Service-Service, sondern Frontend-Service-Kommunikation nutzen. Bei Services untereinander ist ja egal, ob "eine Api" (das Gateway) oder mehrere (jeder Service einzeln), das Gateway kann's da aber manchmal komplizierter machen
 
Krass! Das ist ja echt einfach. Zuul heißt es genau. Danke für deine tolle Hilfe, ich weiß das echt sehr zu schätzen! Tjaaa dann fehlt mir jetzt nur noch was zu View, dann kann ich loslegen, versuche mich grad mit Vaadin, ist das eine gute Idee? Da gibts aber auch wieder Vaadin mit Spring, Vaadin mit Spring Boot ohne Spring boot, herbe da soll einer durch sehen. React soll wohl super sein aber ich hab echt keine Lust auf Java Script, da grault es mir vor das irgendwie mal lernen zu müssen.
 
Im Prinzip kannst du das auch mit JSF machen (kann ja durchaus auf einem EE-Server laufen), musst dann entweder ein festes Gateway haben oder das ganze rudimentär an Eureka anbinden (sollte über die REST-APIckein großes Problem sein).


React und allgemein modernes Javascript ist gar nicht mehr sooo schlimm, kann ja durchaus auch Typescript nutzen und ist dann zb typisiert unterwegs,
 
mal andersherum gedacht.... könnte ich nicht auch ein Programm in FX schreiben mit der Einfachheit von Spring boot? Sprich jeder user hat eine eigene FX Anwendung am laufen die sich über rest mit den services verbindet? Darin kann er dann daten eingeben und sonst was starten. Der eigentliche Job (das stetige updaten von Produktdaten in die DB) erfolgt dann eh automatisiert auf dem server, dazu braucht es kein zutun vom user. Dann ist natürlich wieder der Nachteil; UI Updates müssen verteilt werden
 
mrbrown ich brauch deine Hilfe :D JSF hab ich nun mit Spring boot zum laufen bekommen auf Payara Micro. Nun will ich den login realisieren, finde aber kein vollständiges tutorial für tenant Datenbank Handling. Oder ich bin zu doof das wozu verstehen. Hast du was sinnvolles zur Hand?
 
Jeder User muss eine eigene Datenbank bekommen. Die Daten dürfen nicht gemeinsam in einer DB gespeichert sein. Während sich der User einlogged, muss dann entsprechend mit der richtigen Datenbank gearbeitet werden.

Nun habe ich einen DB Service, der per REST Produktdaten anlegt, herausgibt usw. Wenn ein anderer Service diese DBService API anspricht, muss der DB Service auch entsprechend Daten aus der korrekten Datenbank holen/schreiben. Je nach dem was in der URI als Tenant angegeben wurde.

Ich hoffe ich habe das Thema richtig verstanden
 
Das spiel ich mal durch danke. Angenommen ich habe 100 Datenbanken, wie zum Geier Update ich die Alle, wenn es neue Tabellen oder so gibt?! Gibts da eine Automatik? Oder schreibt man sich da selber einen "Updater" der die Änderungsscripte ausführt?
 
Warum wird in dem Beispiel Jersey genutzt? Spring boot hat doch eigenes Framework für REST oder? Hat das was zu sagen oder hab ich was falsch verstanden?
 
Warum wird in dem Beispiel Jersey genutzt? Spring boot hat doch eigenes Framework für REST oder? Hat das was zu sagen oder hab ich was falsch verstanden?
Spring Boot ist im Grunde genommen eine "opinionated" Zusammenstellung von third-party Libraries zu einem funktionierenden Ganzen: Jersey als JAX-RS Implementierung, Tomcat (oder Jetty) als Servlet Container, Hibernate als JPA Implementierung, Jackson fürs JSON Marshalling, etc... und natürlich Spring Framework als DI-Container und Spring Web MVC mit seinen eigenen Annotationen und Konfigurationen, das sich den darunterliegenden Libraries (Tomcat, Jersey und Jackson) bedient und diese konfiguriert.
 
Ok, vielen Dank! Wenn ich das Projekt aus dem Link mit Eclipse starte, kommt schon mal ne Antwort von der Api (zwar nicht was ich sehen will, aber immer hin)

Wenn ich das Ganze per Terminal starten will kommt

kein Hauptmanifestattribut, in database-service.jar

und es startet nichts, hast du ne Idee woran das liegen kann?
 
Wenn ich das Ganze per Terminal starten will kommt
kein Hauptmanifestattribut, in database-service.jar
und es startet nichts, hast du ne Idee woran das liegen kann?
Wenn du das Projekt mit Maven baust (z.B. mit `mvn clean package`), dann entsteht standardmäßig kein "executable Jar". Spring Boot bietet hierfür aber ein Plugin an, was alle Dependencies hinzufügt und ein executable jar baut.
Siehe hierzu: https://docs.spring.io/spring-boot/docs/current/reference/html/build-tool-plugins-maven-plugin.html#build-tool-plugins-maven-plugin
 
Das hab ich drin.

Code:
<build>
        <plugins>
            <plugin>
                <artifactId>maven-compiler-plugin</artifactId>
                <configuration>
                    <source>1.8</source>
                    <target>1.8</target>
                </configuration>
            </plugin>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <version>2.0.2.RELEASE</version>
            </plugin>
        </plugins>
        <finalName>database-service</finalName>
    </build>
 
beim bauen kommt noch folgende Meldung
[WARNING] 'build.plugins.plugin.version' for org.apache.maven.plugins:maven-compiler-plugin is missing. @ line 17, column 12

obwohl das drin ist
 
Angenommen ich habe 100 Datenbanken, wie zum Geier Update ich die Alle, wenn es neue Tabellen oder so gibt?! Gibts da eine Automatik? Oder schreibt man sich da selber einen "Updater" der die Änderungsscripte ausführt?
Sowas würde man sowieso automatisieren, zB mit Liquibase, ob man dann eine oder 100 ändert, macht keinen wirklichen Unterschied mehr.
Warum wird in dem Beispiel Jersey genutzt? Spring boot hat doch eigenes Framework für REST oder? Hat das was zu sagen oder hab ich was falsch verstanden?
Jersey ist da egal, geht genauso mit allem anderem (bis auf in dem Beispiel das Filter registrieren, dazu gibt es aber zig Beispiele)
 
Vielen dank, scheint du hast voll Plan :) gibt es noch ne alternative zu der db thematik? Könnte ich nicht eine tabelle erstellen in der die zugangsdaten zu den kundendatenbanken sind, wenn dann die view was aus der db braucht, gibt sie bei der rest anfrage den nutzer mit an. Dann schaut der datenbankservice nach, aus welcher datenbank etwas geholt werden soll. Nur mal so als alternative. Oder könnte man für jeden kunden einen eigenen server/service aufstarten der auf einer eigenen domain läuft, sodass der kunde das gefühl hat er logged sich nicht auf einem portal ein sondern hat ein eigenes programm? Mit diesem tenant ist mir irgendwie nicht geheuer
 
Könnte ich nicht eine tabelle erstellen in der die zugangsdaten zu den kundendatenbanken sind, wenn dann die view was aus der db braucht, gibt sie bei der rest anfrage den nutzer mit an. Dann schaut der datenbankservice nach, aus welcher datenbank etwas geholt werden soll. Nur mal so als alternative.
Das wäre im wesentlichen das gleiche wie jetzt - wo die genutzte Datenbank her kommt, ist im wesentlichen egal.
Oder könnte man für jeden kunden einen eigenen server/service aufstarten der auf einer eigenen domain läuft, sodass der kunde das gefühl hat er logged sich nicht auf einem portal ein sondern hat ein eigenes programm?
Das wäre auch Problemlos möglich - grad in Verbindung mit Zuul dürfte das recht leicht umzusetzen sein.

Mit diesem tenant ist mir irgendwie nicht geheuer
Warum nicht? ;)
 
Hmm ich baue lieber immer gern selber was.

Ich würde jetzt zb in meiner view einen rest client einbauen, der sagen wir preise aus der datenbank holen soll. Als uri würde er dann /kundennummer/artikelnummer in der uri übergeben. Der empfangende server würde dann die kundennummer nehmen, aus der kundenDB die zugangsdaten für die kundendatenbank holen und damit eine verbindung aufbauen um die preise zu holen?

Zuul hab ich auch im Einsatz, das wäre ja echt cool! Aber wie starte ich einen service speziell für eine Kunden? Über die args wäre eine Möglichkeit oder?
 
Ich würde jetzt zb in meiner view einen rest client einbauen, der sagen wir preise aus der datenbank holen soll. Als uri würde er dann /kundennummer/artikelnummer in der uri übergeben. Der empfangende server würde dann die kundennummer nehmen, aus der kundenDB die zugangsdaten für die kundendatenbank holen und damit eine verbindung aufbauen um die preise zu holen?
Ginge schon, aber der Weg über zwei Datenbanken dürfte komplizierter sein, als der über eine.

Zuul hab ich auch im Einsatz, das wäre ja echt cool! Aber wie starte ich einen service speziell für eine Kunden? Über die args wäre eine Möglichkeit oder?
z.B, kommt aber auch drauf an, wie die sich unterscheiden.
Müssen sich dann nur mit entsprechender Kennung beim Eureka-Server registrieren und Zuul leitet das dann an den jeweils passenden Server weiter.
 
Wenn man da tenant macht ist es doch aber auch so oder? Da werden doch die Zugangsdaten für die Kundendaten auch in einer db gespeichert oder irre ich mich und die werden in einer properties gespeichert? Denn zur Laufzeit kommen neue kunden dazu, sodass neue db zugangsdaten abgelegt werden müssen. Was ja im propertiesfile nicht wirklich automatisch möglich wäre
 
Ja, wenn die Daten natürlich aus einer DB kommen müssen, müssen sie aus einer DB kommen ;)

Allerdings bietet Spring Cloud auch Lösungen zum Laden und Aktualisieren von Properties über andere Server.
 
Hab grad noch ne Frage. Angenommen ich will in einem Service ein Pojo "User" erstellen, welches ich auch in einem anderen Service brauche. Kann mann dann nicht einen Provider-Service erstellen aus dem man die Pojos nimmt? Sonst müsste ich ja bei jeder Pojo-Änderung in jedem Service alles ändern.
 
Zb ein Service gibt als json ein User Objekt zurück. Dieses Objekt wird von einem anderen Service gelesen und auch wieder in ein Objekt "User" gemapped
 
Genau und wie mach ich das? einen eigenen "Service" Dafür bereit stellen, welchen in in den anderen Services überlesen Dependency verwende?

Edit:
Oder so:

Habe einen datbase-service, der mir die User aus der DB holt und per REST bereitstellt. Der Service "Frontend", fragt bei "Database" den User ab, ob er existiert (Login zb)

Könnte ich auch aus der Entity, im Frontendservices ein neues Objekt erzeugen und damit arbeiten? (Müsste dann auch hier, den database-service in den frontend-service via pom bringen
 
Genau und wie mach ich das? einen eigenen "Service" Dafür bereit stellen, welchen in in den anderen Services überlesen Dependency verwende?
Ja, die Domänen-Klassen, die geteilt werde sollen (nicht die Services) in ein eigenes Projekt, und das als Dependency von allen, die die Klassen brauchen.

Habe einen datbase-service, der mir die User aus der DB holt und per REST bereitstellt. Der Service "Frontend", fragt bei "Database" den User ab, ob er existiert (Login zb)

Könnte ich auch aus der Entity, im Frontendservices ein neues Objekt erzeugen und damit arbeiten? (Müsste dann auch hier, den database-service in den frontend-service via pom bringen
Man würde aus dem Database-Service eher einen User-Service machen (jeder Service kümmert sich üblicherweise selbst um seine Datenbank), aber ja, der würd das über Rest bereitstellen, und die anderen Services können damit machen, was auch immer sie wollen
 
Naja, deine Problemdomäne? Das, was im Domänenmodell dargestellt ist, und was oft die Grundlage von Microservices ist. ZB Nutzer, Artikel, ...
Ich wollte dem datenbankservice verschiedene Aufgaben geben; User resource, Artikel Ressource usw
Damit hat man dann doch wieder alle eigentlich unabhängigen Dinge in einem (Micro-)Service gebündelt, das will man ja eigentlich vermeiden
 
Und zu Guter letzt, müsste ich noch die Services untereinander absichern, reicht es per http Auth? Ich lese immer wieder was von JWT
 
Aber man soll ja auch doppelten Code meiden
Viel doppelter Code fällt da nicht an, der für Article und der für Nutzer zb hat ja nicht allzu viel miteinander zu tun.

Und zu Guter letzt, müsste ich noch die Services untereinander absichern, reicht es per http Auth? Ich lese immer wieder was von JWT
JWT ist dafür schon ganz nett, hier ist eine grobe Erklärung dazu: https://stormpath.com/blog/microservices-jwt-spring-boot
 
Passende Stellenanzeigen aus deiner Region:
Anzeige

Anzeige

Anzeige
Oben