JSF Frage zu Synchronisation zwischen SessionScoped beans

Denny1989

Aktives Mitglied
Hallo.
ich bin grad dabei eine kleine Portalseite zu erstellen.

Es gibt einen normalen Nutzer der sich nciht einloggen muss. Der kann ein Lokal auswählen über das er sich informieren möchte. Da sich das auf mehrere Seiten verteilt nehme ich ein @SessionScoped bean und halte dieses "aktuelleLokal" vor.


Es gibt darüber hinaus einen "Lokalbesitzer" der natürlich in seiner session ein normaler nutzer ist also auch ein lokal auswählen kann und sich darüberhinaus anmelden / einloggen kann um sein eigenes lokal zu verwalen. Dafür nutze ich ein zweites @SessionScoped bean welches für verwaltungsaufgaben veranwortlich ist. Hier speichere ich das "eigeneLokal".

Das eigeneLokal kann geändert werden (Name anschrift usw). das mache ich im @Stateless DataService mit em.merge(eigeneLokal);. Jetzt weiß zwar der SessionScope des Lokalbesitzers dass der laden anders heißt, weil es ja hier rüber geändert wurde (z.B: über Formeingaben), aber die normale Nutzer SessionScope bekommt das nicht mit.

Jetzt habe ich folgende Lösungsansätze:
1) beim abruf des lokals in der Nutzersession immer wieder das Objekt an hand der Id neu aus der DB holen.

2) im @SessionScoped des Lokalbesitzers den Nutzer SessionScoped injizieren und ggf. (im Falle die stimmten vorher überein) die variable "aktuelleLokal" = "eigeneLokal" (das zuvor geändert wurde)


So nun nochmal zum Verstäändnis zusammengefasst. ich habe 2 x @SessionScoped und 2x @Stateless für Datenservices mit jeweils anderen Verantwortlichenkeiten bzw. "Berechtigungen".

Nun die Frage:
Sollte das 1. @SessionScoped beim abgefragt werden der Variable "aktuelleLokal" nicht schon gemerkt haben dass dieses Entity sich geändert hat? Ist das nicht einer der vorteile dieser managed Entity Sache? die beiden Variablen "aktuelleLokal" und "eigeneLokal" sollten doch nur auf ein Entity zeigen das in einem PersistenceContext liegt oder? und bei em.merge soltle sich diese Objekt updaten und auch für beide referenzen zur verfügung stehen!?

Entschuldigt bitte meine Unfähigkeit mich Fachkundig auszudrücken.
 

FArt

Top Contributor
Entity über JPA, oder was ist dein "Datenservice"?

Interessant ist nicht der Scope der Beans, sondern sind die Transaktionsgrenzen und das Transaktionsisolationslevel.
 

Denny1989

Aktives Mitglied
naja mein Datenservice ist einfach nur ne sammlung von funktionen á la
Java:
public List<Canteen> getCanteens() {
		return em.createNamedQuery(Canteen.FIND_ACTIVE_ALL, Canteen.class)
				.getResultList();
	}
 
N

nillehammer

Gast
Das Problem entsteht nicht durch fehlende Synchronisation mit der DB oder verfuddelte Transaktionsgrenzen, sondern durch Speichern von "aktuellesLokal" in der (Web-)Session.

Erliege nicht der Versuchung, über Caching in der Session Datenbankabfragen zu vermeiden. Wenn überhaupt nötig, nutze das Caching Deines Persistence-Providers. Nur hier bist Du sicher, dass Du gültige Daten bekommst. Also, verzichte auf das Speichern von "aktuellesLokal" in der Session und hole Dir es jedes Mal neu.
 
Zuletzt bearbeitet von einem Moderator:

FArt

Top Contributor
Annahme: hinter "aktuelles Lokal" steckt die Entity, und nicht nur dessen gespeicherter (u.U. alter) Wert... oder ?
 
N

nillehammer

Gast
Annahme: hinter "aktuelles Lokal" steckt die Entity, und nicht nur dessen gespeicherter (u.U. alter) Wert... oder ?
Hmm? Das ist doch das gleiche. Die Entity wird aus der DB geladen und ist im Prinzip schon "alt" (also möglicherweise nicht mehr akutell), wenn sie detached ist. Deswegen eben nicht in der Web-Session speichern, sondern für jeden Request neu holen.
 

FArt

Top Contributor
Hmm? Das ist doch das gleiche. Die Entity wird aus der DB geladen und ist im Prinzip schon "alt" (also möglicherweise nicht mehr akutell), wenn sie detached ist. Deswegen eben nicht in der Web-Session speichern, sondern für jeden Request neu holen.

Das kommt doch auf den conversational state an, oder? Dann ist das Objekt reattached (in einer Conversation)...
 
Zuletzt bearbeitet:
N

nillehammer

Gast
Gut, aber das hat dann doch trotzdem nichts mit dem State der Entity zu tun. Bei JPA ist es nunmal so, dass Entities nur solange "managed" sind, so lange der PersistenceContext offen ist. Sobald der zu ist, sind es wieder POJOs. Wenn ich ein solches in der Websession speichere, repräsentiert es einen Zustand, wie er zum Zeitpunkt des Landens mal war, aber nicht mehr sein muss.

Außerdem ist das Conversation Pattern doch mehr für Wizard-Artige Dialoge gedacht, wo ich Daten über mehrere Seiten hinweg pflegen muss. Um die Aktualität von angezeigten Daten zu garantieren ist es meiner Meinung nach ungeeignet. Deswegen eben auch mein Tipp, die Daten bei jedem Request neu zu holen und nur falls nötig auf das Caching des Persistence Providers zurückzugreifen.
 

FArt

Top Contributor
Den Conversational State kann ich bei SFSB auch u.U. gut brauchen, da werden dann eben die Entitäten beim nächsten Call wieder attached. Ist halt der Unterschied zwischen der Transaktion und dem Status des PersistentContext. Ob es pures JPA ist hat TS nicht gesagt, aber ich nehme es auch an. Ich wollte auch nur mal ein paar Begriffe in den Raum werfen, mit den der TS sich befassen sollte, denn da hat er noch Nachholbedarf. Wenn die Möglichkeit fehlt, sich sauber auszudrücken, fehlt in der Regel auch das Basisverständnis.
 

Ähnliche Java Themen

Neue Themen


Oben