2017-08-06 3 views
0

Nous avons une application Java qui traite 100k paquets par minute. Les paquets incluent les détails d'opération de l'utilisateur et pour une opération d'un utilisateur. Il peut y avoir 3 à 14 paquets pour une opération. Tous les paquets reçus contiennent des données uniques pour l'opération et malheureusement l'opération n'a pas d'identifiant. Pour cette raison, nous utilisons l'identifiant utilisateur et la date d'opération pour fusionner les paquets qui appartiennent à la même opération. Il nous est garanti que nous recevrons tous les colis pour une opération utilisateur en 15 minutes maximum. Donc, pour fusionner tous les paquets avant de persister, nous mettons en cache tous les paquets reçus sur Hazelcast et insérons les paquets quand les paquets OPSTART ou OPEND sont reçus. Les paquets expirent à 20 minutes. Cependant, après une heure ou deux, l'espace dans les tas de Hazelcast dépasse 70%.Hazelcast Out of Memory

c.h.internal.diagnostics.HealthMonitor : [192.168.2.42]:5701 [dev] [3.7.5] processors=4, physical.memory.total=15.7G, physical.memory.free=6.1G, swap.space.total=2.0G, swap.space.free=2.0G, heap.memory.used=3.1G, heap.memory.free=267.1M, heap.memory.total=3.3G, heap.memory.max=3.5G, heap.memory.used/total=92.15%, heap.memory.used/max=88.02%, minor.gc.count=71, minor.gc.time=4628ms, major.gc.count=10, major.gc.time=7186ms, load.process=0.00%, load.system=0.01%, load.systemAverage=0.00%, thread.count=502, thread.peakCount=502, cluster.timeDiff=-121091, event.q.size=0, executor.q.async.size=0, executor.q.client.size=0, executor.q.query.size=0, executor.q.scheduled.size=0, executor.q.io.size=0, executor.q.system.size=0, executor.q.operations.size=0, executor.q.priorityOperation.size=0, operations.completed.count=4722977, executor.q.mapLoad.size=0, executor.q.mapLoadAllKeys.size=0, executor.q.cluster.size=0, executor.q.response.size=0, operations.running.count=0, operations.pending.invocations.percentage=0.00%, operations.pending.invocations.count=50, proxy.count=0, clientEndpoint.count=0, connection.active.count=1, client.connection.count=0, connection.count=1 

Et après environ 1 heure et demi une heure plus tard, les invocations commencent à expirer. Après 2 à 3 heures après le démarrage, Hazelcast émet une exception de mémoire insuffisante et le déploiement se termine.

4 Go de mémoire devraient suffire pour les données qui ont été mises en cache. Nous n'avons pas pu trouver les causes de Hazelcast pour lancer une exception de mémoire insuffisante. Quelle pourrait être la raison? Que pouvons-nous faire pour comprendre le problème?

+0

Comment avez-vous calculé le besoin, si vous dites 4Go devrait être suffisant? Avez-vous regardé une décharge de la tête encore? – noctarius

+0

Il semble que le processus "expire" n'évince pas les paquets. Cela, ou un autre type de fuite de mémoire. – rghome

Répondre

1

La meilleure façon de déterminer la cause de l'OOME est de créer un tas et de l'analyser et de voir comment la mémoire est conservée. Probablement ce sera un grand nombre de tableaux d'octets. Si vous vérifiez les références entrantes à ces tableaux d'octets et les agrégez (jprofiler a un excellent support pour cela), il est très facile de déterminer la chaîne de classes retenant la mémoire.