1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 package org.eclipse.jetty.server.session;
21
22 import java.io.ByteArrayInputStream;
23 import java.io.ByteArrayOutputStream;
24 import java.io.InputStream;
25 import java.io.ObjectOutputStream;
26 import java.sql.Connection;
27 import java.sql.PreparedStatement;
28 import java.sql.ResultSet;
29 import java.sql.SQLException;
30 import java.util.ArrayList;
31 import java.util.HashSet;
32 import java.util.Iterator;
33 import java.util.Map;
34 import java.util.Set;
35 import java.util.concurrent.ConcurrentHashMap;
36 import java.util.concurrent.TimeUnit;
37 import java.util.concurrent.atomic.AtomicReference;
38
39 import javax.servlet.http.HttpServletRequest;
40 import org.eclipse.jetty.server.handler.ContextHandler;
41 import org.eclipse.jetty.server.session.JDBCSessionIdManager.SessionTableSchema;
42 import org.eclipse.jetty.util.ClassLoadingObjectInputStream;
43 import org.eclipse.jetty.util.log.Log;
44 import org.eclipse.jetty.util.log.Logger;
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70 public class JDBCSessionManager extends AbstractSessionManager
71 {
72 private static final Logger LOG = Log.getLogger(JDBCSessionManager.class);
73
74 private ConcurrentHashMap<String, Session> _sessions;
75 protected JDBCSessionIdManager _jdbcSessionIdMgr = null;
76 protected long _saveIntervalSec = 60;
77 protected SessionTableSchema _sessionTableSchema;
78
79
80
81
82
83
84
85
86
87 public class Session extends MemSession
88 {
89 private static final long serialVersionUID = 5208464051134226143L;
90
91
92
93
94 protected boolean _dirty=false;
95
96
97
98
99
100 protected long _cookieSet;
101
102
103
104
105
106 protected long _expiryTime;
107
108
109
110
111
112 protected long _lastSaved;
113
114
115
116
117
118 protected String _lastNode;
119
120
121
122
123
124 protected String _virtualHost;
125
126
127
128
129
130 protected String _rowId;
131
132
133
134
135
136 protected String _canonicalContext;
137
138
139
140
141
142
143
144 protected Session (HttpServletRequest request)
145 {
146 super(JDBCSessionManager.this,request);
147 int maxInterval=getMaxInactiveInterval();
148 _expiryTime = (maxInterval <= 0 ? 0 : (System.currentTimeMillis() + maxInterval*1000L));
149 _virtualHost = JDBCSessionManager.getVirtualHost(_context);
150 _canonicalContext = canonicalize(_context.getContextPath());
151 _lastNode = getSessionIdManager().getWorkerName();
152 }
153
154
155
156
157
158
159
160
161
162 protected Session (String sessionId, String rowId, long created, long accessed, long maxInterval)
163 {
164 super(JDBCSessionManager.this, created, accessed, sessionId);
165 _rowId = rowId;
166 super.setMaxInactiveInterval((int)maxInterval);
167 _expiryTime = (maxInterval <= 0 ? 0 : (System.currentTimeMillis() + maxInterval*1000L));
168 }
169
170
171 protected synchronized String getRowId()
172 {
173 return _rowId;
174 }
175
176 protected synchronized void setRowId(String rowId)
177 {
178 _rowId = rowId;
179 }
180
181 public synchronized void setVirtualHost (String vhost)
182 {
183 _virtualHost=vhost;
184 }
185
186 public synchronized String getVirtualHost ()
187 {
188 return _virtualHost;
189 }
190
191 public synchronized long getLastSaved ()
192 {
193 return _lastSaved;
194 }
195
196 public synchronized void setLastSaved (long time)
197 {
198 _lastSaved=time;
199 }
200
201 public synchronized void setExpiryTime (long time)
202 {
203 _expiryTime=time;
204 }
205
206 public synchronized long getExpiryTime ()
207 {
208 return _expiryTime;
209 }
210
211
212 public synchronized void setCanonicalContext(String str)
213 {
214 _canonicalContext=str;
215 }
216
217 public synchronized String getCanonicalContext ()
218 {
219 return _canonicalContext;
220 }
221
222 public void setCookieSet (long ms)
223 {
224 _cookieSet = ms;
225 }
226
227 public synchronized long getCookieSet ()
228 {
229 return _cookieSet;
230 }
231
232 public synchronized void setLastNode (String node)
233 {
234 _lastNode=node;
235 }
236
237 public synchronized String getLastNode ()
238 {
239 return _lastNode;
240 }
241
242 @Override
243 public void setAttribute (String name, Object value)
244 {
245 Object old = changeAttribute(name, value);
246 if (value == null && old == null)
247 return;
248
249 _dirty = true;
250 }
251
252 @Override
253 public void removeAttribute (String name)
254 {
255 Object old = changeAttribute(name, null);
256 if (old != null)
257 _dirty=true;
258 }
259
260 @Override
261 protected void cookieSet()
262 {
263 _cookieSet = getAccessed();
264 }
265
266
267
268
269
270
271
272 @Override
273 protected boolean access(long time)
274 {
275 synchronized (this)
276 {
277 if (super.access(time))
278 {
279 int maxInterval=getMaxInactiveInterval();
280 _expiryTime = (maxInterval <= 0 ? 0 : (time + maxInterval*1000L));
281 return true;
282 }
283 return false;
284 }
285 }
286
287
288
289
290
291
292
293
294
295 @Override
296 public void setMaxInactiveInterval(int secs)
297 {
298 synchronized (this)
299 {
300 super.setMaxInactiveInterval(secs);
301 int maxInterval=getMaxInactiveInterval();
302 _expiryTime = (maxInterval <= 0 ? 0 : (System.currentTimeMillis() + maxInterval*1000L));
303
304 try
305 {
306 updateSessionAccessTime(this);
307 }
308 catch (Exception e)
309 {
310 LOG.warn("Problem saving changed max idle time for session "+ this, e);
311 }
312 }
313 }
314
315
316
317
318
319
320 @Override
321 protected void complete()
322 {
323 synchronized (this)
324 {
325 super.complete();
326 try
327 {
328 if (isValid())
329 {
330 if (_dirty)
331 {
332
333
334 save(true);
335 }
336 else if ((getAccessed() - _lastSaved) >= (getSaveInterval() * 1000L))
337 {
338 updateSessionAccessTime(this);
339 }
340 }
341 }
342 catch (Exception e)
343 {
344 LOG.warn("Problem persisting changed session data id="+getId(), e);
345 }
346 finally
347 {
348 _dirty=false;
349 }
350 }
351 }
352
353 protected void save() throws Exception
354 {
355 synchronized (this)
356 {
357 try
358 {
359 updateSession(this);
360 }
361 finally
362 {
363 _dirty = false;
364 }
365 }
366 }
367
368 protected void save (boolean reactivate) throws Exception
369 {
370 synchronized (this)
371 {
372 if (_dirty)
373 {
374
375
376 willPassivate();
377 updateSession(this);
378 if (reactivate)
379 didActivate();
380 }
381 }
382 }
383
384
385 @Override
386 protected void timeout() throws IllegalStateException
387 {
388 if (LOG.isDebugEnabled())
389 LOG.debug("Timing out session id="+getClusterId());
390 super.timeout();
391 }
392
393
394 @Override
395 public String toString ()
396 {
397 return "Session rowId="+_rowId+",id="+getId()+",lastNode="+_lastNode+
398 ",created="+getCreationTime()+",accessed="+getAccessed()+
399 ",lastAccessed="+getLastAccessedTime()+",cookieSet="+_cookieSet+
400 ",maxInterval="+getMaxInactiveInterval()+",lastSaved="+_lastSaved+",expiry="+_expiryTime;
401 }
402 }
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425 public void setSaveInterval (long sec)
426 {
427 _saveIntervalSec=sec;
428 }
429
430 public long getSaveInterval ()
431 {
432 return _saveIntervalSec;
433 }
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448 public void cacheInvalidate (Session session)
449 {
450
451 }
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470 @Override
471 public Session getSession(String idInCluster)
472 {
473 Session session = null;
474
475 synchronized (this)
476 {
477 Session memSession = (Session)_sessions.get(idInCluster);
478
479
480
481
482
483
484
485
486
487
488 long now = System.currentTimeMillis();
489 if (LOG.isDebugEnabled())
490 {
491 if (memSession==null)
492 LOG.debug("getSession("+idInCluster+"): not in session map,"+
493 " now="+now+
494 " lastSaved="+(memSession==null?0:memSession._lastSaved)+
495 " interval="+(_saveIntervalSec * 1000L));
496 else
497 LOG.debug("getSession("+idInCluster+"): in session map, "+
498 " hashcode="+memSession.hashCode()+
499 " now="+now+
500 " lastSaved="+(memSession==null?0:memSession._lastSaved)+
501 " interval="+(_saveIntervalSec * 1000L)+
502 " lastNode="+memSession._lastNode+
503 " thisNode="+getSessionIdManager().getWorkerName()+
504 " difference="+(now - memSession._lastSaved));
505 }
506
507 try
508 {
509 if (memSession==null)
510 {
511 if (LOG.isDebugEnabled())
512 LOG.debug("getSession("+idInCluster+"): no session in session map. Reloading session data from db.");
513 session = loadSession(idInCluster, canonicalize(_context.getContextPath()), getVirtualHost(_context));
514 }
515 else if ((now - memSession._lastSaved) >= (_saveIntervalSec * 1000L))
516 {
517 if (LOG.isDebugEnabled())
518 LOG.debug("getSession("+idInCluster+"): stale session. Reloading session data from db.");
519 session = loadSession(idInCluster, canonicalize(_context.getContextPath()), getVirtualHost(_context));
520 }
521 else
522 {
523 if (LOG.isDebugEnabled())
524 LOG.debug("getSession("+idInCluster+"): session in session map");
525 session = memSession;
526 }
527 }
528 catch (Exception e)
529 {
530 LOG.warn("Unable to load session "+idInCluster, e);
531 return null;
532 }
533
534
535
536 if (session != null)
537 {
538
539 if (!session.getLastNode().equals(getSessionIdManager().getWorkerName()) || memSession==null)
540 {
541
542 if (session._expiryTime <= 0 || session._expiryTime > now)
543 {
544 if (LOG.isDebugEnabled())
545 LOG.debug("getSession("+idInCluster+"): lastNode="+session.getLastNode()+" thisNode="+getSessionIdManager().getWorkerName());
546
547 session.setLastNode(getSessionIdManager().getWorkerName());
548 _sessions.put(idInCluster, session);
549
550
551 try
552 {
553 updateSessionNode(session);
554 session.didActivate();
555 }
556 catch (Exception e)
557 {
558 LOG.warn("Unable to update freshly loaded session "+idInCluster, e);
559 return null;
560 }
561 }
562 else
563 {
564 if (LOG.isDebugEnabled())
565 LOG.debug("getSession ({}): Session has expired", idInCluster);
566
567
568 _jdbcSessionIdMgr.removeSession(idInCluster);
569 session=null;
570 }
571
572 }
573 else
574 {
575
576 session = memSession;
577 if (LOG.isDebugEnabled())
578 LOG.debug("getSession({}): Session not stale {}", idInCluster,session);
579 }
580 }
581 else
582 {
583
584 LOG.debug("getSession({}): No session in database matching id={}",idInCluster,idInCluster);
585 }
586
587 return session;
588 }
589 }
590
591
592
593
594
595
596
597 @Override
598 public int getSessions()
599 {
600 return _sessions.size();
601 }
602
603
604
605
606
607
608
609 @Override
610 public void doStart() throws Exception
611 {
612 if (_sessionIdManager==null)
613 throw new IllegalStateException("No session id manager defined");
614
615 _jdbcSessionIdMgr = (JDBCSessionIdManager)_sessionIdManager;
616 _sessionTableSchema = _jdbcSessionIdMgr.getSessionTableSchema();
617
618 _sessions = new ConcurrentHashMap<String, Session>();
619
620 super.doStart();
621 }
622
623
624
625
626
627
628
629 @Override
630 public void doStop() throws Exception
631 {
632 super.doStop();
633 _sessions.clear();
634 _sessions = null;
635 }
636
637 @Override
638 protected void shutdownSessions()
639 {
640
641
642 long gracefulStopMs = getContextHandler().getServer().getStopTimeout();
643 long stopTime = 0;
644 if (gracefulStopMs > 0)
645 stopTime = System.nanoTime() + (TimeUnit.NANOSECONDS.convert(gracefulStopMs, TimeUnit.MILLISECONDS));
646
647 ArrayList<Session> sessions = (_sessions == null? new ArrayList<Session>() :new ArrayList<Session>(_sessions.values()) );
648
649
650 while (sessions.size() > 0 && ((stopTime > 0 && (System.nanoTime() < stopTime)) || (stopTime == 0)))
651 {
652 for (Session session : sessions)
653 {
654 try
655 {
656 session.save(false);
657 }
658 catch (Exception e)
659 {
660 LOG.warn(e);
661 }
662 _sessions.remove(session.getClusterId());
663 }
664
665
666 if (stopTime == 0)
667 break;
668
669
670 sessions=new ArrayList<Session>(_sessions.values());
671 }
672 }
673
674
675
676
677
678
679 public void renewSessionId (String oldClusterId, String oldNodeId, String newClusterId, String newNodeId)
680 {
681 Session session = null;
682 try
683 {
684 session = (Session)_sessions.remove(oldClusterId);
685 if (session != null)
686 {
687 synchronized (session)
688 {
689 session.setClusterId(newClusterId);
690 session.setNodeId(newNodeId);
691 _sessions.put(newClusterId, session);
692 updateSession(session);
693 }
694 }
695 }
696 catch (Exception e)
697 {
698 LOG.warn(e);
699 }
700
701 super.renewSessionId(oldClusterId, oldNodeId, newClusterId, newNodeId);
702 }
703
704
705
706
707
708
709
710
711 protected void invalidateSession (String idInCluster)
712 {
713 Session session = (Session)_sessions.get(idInCluster);
714
715 if (session != null)
716 {
717 session.invalidate();
718 }
719 }
720
721
722
723
724
725
726
727 @Override
728 protected boolean removeSession(String idInCluster)
729 {
730 Session session = (Session)_sessions.remove(idInCluster);
731 try
732 {
733 if (session != null)
734 deleteSession(session);
735 }
736 catch (Exception e)
737 {
738 LOG.warn("Problem deleting session id="+idInCluster, e);
739 }
740 return session!=null;
741 }
742
743
744
745
746
747
748
749 @Override
750 protected void addSession(AbstractSession session)
751 {
752 if (session==null)
753 return;
754
755 _sessions.put(session.getClusterId(), (Session)session);
756
757 try
758 {
759 synchronized (session)
760 {
761 session.willPassivate();
762 storeSession(((JDBCSessionManager.Session)session));
763 session.didActivate();
764 }
765 }
766 catch (Exception e)
767 {
768 LOG.warn("Unable to store new session id="+session.getId() , e);
769 }
770 }
771
772
773
774
775
776
777
778 @Override
779 protected AbstractSession newSession(HttpServletRequest request)
780 {
781 return new Session(request);
782 }
783
784
785
786
787
788
789
790
791
792
793 protected AbstractSession newSession (String sessionId, String rowId, long created, long accessed, long maxInterval)
794 {
795 return new Session(sessionId, rowId, created, accessed, maxInterval);
796 }
797
798
799
800
801
802
803
804 @Override
805 public boolean removeSession(AbstractSession session, boolean invalidate)
806 {
807
808 boolean removed = super.removeSession(session, invalidate);
809
810 if (removed)
811 {
812 if (!invalidate)
813 {
814 session.willPassivate();
815 }
816 }
817
818 return removed;
819 }
820
821
822
823
824
825
826
827
828 protected Set<String> expire (Set<String> sessionIds)
829 {
830
831 if (isStopping() || isStopped())
832 return null;
833
834
835 Thread thread=Thread.currentThread();
836 ClassLoader old_loader=thread.getContextClassLoader();
837
838 Set<String> successfullyExpiredIds = new HashSet<String>();
839 try
840 {
841 Iterator<?> itor = sessionIds.iterator();
842 while (itor.hasNext())
843 {
844 String sessionId = (String)itor.next();
845 if (LOG.isDebugEnabled())
846 LOG.debug("Expiring session id "+sessionId);
847
848 Session session = (Session)_sessions.get(sessionId);
849
850
851 if (session == null)
852 {
853 if (LOG.isDebugEnabled())LOG.debug("Force loading session id "+sessionId);
854 session = loadSession(sessionId, canonicalize(_context.getContextPath()), getVirtualHost(_context));
855 if (session != null)
856 {
857
858
859 _sessions.put(session.getClusterId(), session);
860 }
861 else
862 {
863 if (LOG.isDebugEnabled())
864 LOG.debug("Unrecognized session id="+sessionId);
865 continue;
866 }
867 }
868
869 if (session != null)
870 {
871 session.timeout();
872 successfullyExpiredIds.add(session.getClusterId());
873 }
874 }
875 return successfullyExpiredIds;
876 }
877 catch (Throwable t)
878 {
879 LOG.warn("Problem expiring sessions", t);
880 return successfullyExpiredIds;
881 }
882 finally
883 {
884 thread.setContextClassLoader(old_loader);
885 }
886 }
887
888
889
890
891
892
893
894
895 protected Session loadSession (final String id, final String canonicalContextPath, final String vhost)
896 throws Exception
897 {
898 final AtomicReference<Session> _reference = new AtomicReference<Session>();
899 final AtomicReference<Exception> _exception = new AtomicReference<Exception>();
900 Runnable load = new Runnable()
901 {
902
903
904
905 @SuppressWarnings("unchecked")
906 public void run()
907 {
908 try (Connection connection = getConnection();
909 PreparedStatement statement = _sessionTableSchema.getLoadStatement(connection, id, canonicalContextPath, vhost);
910 ResultSet result = statement.executeQuery())
911 {
912 Session session = null;
913 if (result.next())
914 {
915 long maxInterval = result.getLong(_sessionTableSchema.getMaxIntervalColumn());
916 if (maxInterval == JDBCSessionIdManager.MAX_INTERVAL_NOT_SET)
917 {
918 maxInterval = getMaxInactiveInterval();
919 }
920 session = (Session)newSession(id, result.getString(_sessionTableSchema.getRowIdColumn()),
921 result.getLong(_sessionTableSchema.getCreateTimeColumn()),
922 result.getLong(_sessionTableSchema.getAccessTimeColumn()),
923 maxInterval);
924 session.setCookieSet(result.getLong(_sessionTableSchema.getCookieTimeColumn()));
925 session.setLastAccessedTime(result.getLong(_sessionTableSchema.getLastAccessTimeColumn()));
926 session.setLastNode(result.getString(_sessionTableSchema.getLastNodeColumn()));
927 session.setLastSaved(result.getLong(_sessionTableSchema.getLastSavedTimeColumn()));
928 session.setExpiryTime(result.getLong(_sessionTableSchema.getExpiryTimeColumn()));
929 session.setCanonicalContext(result.getString(_sessionTableSchema.getContextPathColumn()));
930 session.setVirtualHost(result.getString(_sessionTableSchema.getVirtualHostColumn()));
931
932 try (InputStream is = ((JDBCSessionIdManager)getSessionIdManager())._dbAdaptor.getBlobInputStream(result, _sessionTableSchema.getMapColumn());
933 ClassLoadingObjectInputStream ois = new ClassLoadingObjectInputStream(is))
934 {
935 Object o = ois.readObject();
936 session.addAttributes((Map<String,Object>)o);
937 }
938
939 if (LOG.isDebugEnabled())
940 LOG.debug("LOADED session "+session);
941 }
942 else
943 if (LOG.isDebugEnabled())
944 LOG.debug("Failed to load session "+id);
945 _reference.set(session);
946 }
947 catch (Exception e)
948 {
949 _exception.set(e);
950 }
951 }
952 };
953
954 if (_context==null)
955 load.run();
956 else
957 _context.getContextHandler().handle(load);
958
959 if (_exception.get()!=null)
960 {
961
962
963 _jdbcSessionIdMgr.removeSession(id);
964 throw _exception.get();
965 }
966
967 return _reference.get();
968 }
969
970
971
972
973
974
975
976 protected void storeSession (Session session)
977 throws Exception
978 {
979 if (session==null)
980 return;
981
982
983 try (Connection connection = getConnection();
984 PreparedStatement statement = connection.prepareStatement(_jdbcSessionIdMgr._insertSession))
985 {
986 String rowId = calculateRowId(session);
987
988 long now = System.currentTimeMillis();
989 connection.setAutoCommit(true);
990 statement.setString(1, rowId);
991 statement.setString(2, session.getClusterId());
992 statement.setString(3, session.getCanonicalContext());
993 statement.setString(4, session.getVirtualHost());
994 statement.setString(5, getSessionIdManager().getWorkerName());
995 statement.setLong(6, session.getAccessed());
996 statement.setLong(7, session.getLastAccessedTime());
997 statement.setLong(8, session.getCreationTime());
998 statement.setLong(9, session.getCookieSet());
999 statement.setLong(10, now);
1000 statement.setLong(11, session.getExpiryTime());
1001 statement.setLong(12, session.getMaxInactiveInterval());
1002
1003 ByteArrayOutputStream baos = new ByteArrayOutputStream();
1004 ObjectOutputStream oos = new ObjectOutputStream(baos);
1005 oos.writeObject(session.getAttributeMap());
1006 oos.flush();
1007 byte[] bytes = baos.toByteArray();
1008
1009 ByteArrayInputStream bais = new ByteArrayInputStream(bytes);
1010 statement.setBinaryStream(13, bais, bytes.length);
1011
1012
1013 statement.executeUpdate();
1014 session.setRowId(rowId);
1015 session.setLastSaved(now);
1016 }
1017 if (LOG.isDebugEnabled())
1018 LOG.debug("Stored session "+session);
1019 }
1020
1021
1022
1023
1024
1025
1026
1027
1028 protected void updateSession (Session data)
1029 throws Exception
1030 {
1031 if (data==null)
1032 return;
1033
1034 try (Connection connection = getConnection();
1035 PreparedStatement statement = connection.prepareStatement(_jdbcSessionIdMgr._updateSession))
1036 {
1037 long now = System.currentTimeMillis();
1038 connection.setAutoCommit(true);
1039 statement.setString(1, data.getClusterId());
1040 statement.setString(2, getSessionIdManager().getWorkerName());
1041 statement.setLong(3, data.getAccessed());
1042 statement.setLong(4, data.getLastAccessedTime());
1043 statement.setLong(5, now);
1044 statement.setLong(6, data.getExpiryTime());
1045 statement.setLong(7, data.getMaxInactiveInterval());
1046
1047 ByteArrayOutputStream baos = new ByteArrayOutputStream();
1048 ObjectOutputStream oos = new ObjectOutputStream(baos);
1049 oos.writeObject(data.getAttributeMap());
1050 oos.flush();
1051 byte[] bytes = baos.toByteArray();
1052 ByteArrayInputStream bais = new ByteArrayInputStream(bytes);
1053
1054 statement.setBinaryStream(8, bais, bytes.length);
1055 statement.setString(9, data.getRowId());
1056 statement.executeUpdate();
1057
1058 data.setLastSaved(now);
1059 }
1060 if (LOG.isDebugEnabled())
1061 LOG.debug("Updated session "+data);
1062 }
1063
1064
1065
1066
1067
1068
1069
1070
1071 protected void updateSessionNode (Session data)
1072 throws Exception
1073 {
1074 String nodeId = getSessionIdManager().getWorkerName();
1075 try (Connection connection = getConnection();
1076 PreparedStatement statement = connection.prepareStatement(_jdbcSessionIdMgr._updateSessionNode))
1077 {
1078 connection.setAutoCommit(true);
1079 statement.setString(1, nodeId);
1080 statement.setString(2, data.getRowId());
1081 statement.executeUpdate();
1082 }
1083 if (LOG.isDebugEnabled())
1084 LOG.debug("Updated last node for session id="+data.getId()+", lastNode = "+nodeId);
1085 }
1086
1087
1088
1089
1090
1091
1092
1093 private void updateSessionAccessTime (Session data)
1094 throws Exception
1095 {
1096 try (Connection connection = getConnection();
1097 PreparedStatement statement = connection.prepareStatement(_jdbcSessionIdMgr._updateSessionAccessTime))
1098 {
1099 long now = System.currentTimeMillis();
1100 connection.setAutoCommit(true);
1101 statement.setString(1, getSessionIdManager().getWorkerName());
1102 statement.setLong(2, data.getAccessed());
1103 statement.setLong(3, data.getLastAccessedTime());
1104 statement.setLong(4, now);
1105 statement.setLong(5, data.getExpiryTime());
1106 statement.setLong(6, data.getMaxInactiveInterval());
1107 statement.setString(7, data.getRowId());
1108
1109 statement.executeUpdate();
1110 data.setLastSaved(now);
1111 }
1112 if (LOG.isDebugEnabled())
1113 LOG.debug("Updated access time session id="+data.getId()+" with lastsaved="+data.getLastSaved());
1114 }
1115
1116
1117
1118
1119
1120
1121
1122
1123
1124
1125
1126 protected void deleteSession (Session data)
1127 throws Exception
1128 {
1129 try (Connection connection = getConnection();
1130 PreparedStatement statement = connection.prepareStatement(_jdbcSessionIdMgr._deleteSession))
1131 {
1132 connection.setAutoCommit(true);
1133 statement.setString(1, data.getRowId());
1134 statement.executeUpdate();
1135 if (LOG.isDebugEnabled())
1136 LOG.debug("Deleted Session "+data);
1137 }
1138 }
1139
1140
1141
1142
1143
1144
1145
1146
1147 private Connection getConnection ()
1148 throws SQLException
1149 {
1150 return ((JDBCSessionIdManager)getSessionIdManager()).getConnection();
1151 }
1152
1153
1154
1155
1156
1157
1158
1159
1160 private String calculateRowId (Session data)
1161 {
1162 String rowId = canonicalize(_context.getContextPath());
1163 rowId = rowId + "_" + getVirtualHost(_context);
1164 rowId = rowId+"_"+data.getId();
1165 return rowId;
1166 }
1167
1168
1169
1170
1171
1172
1173
1174
1175 private static String getVirtualHost (ContextHandler.Context context)
1176 {
1177 String vhost = "0.0.0.0";
1178
1179 if (context==null)
1180 return vhost;
1181
1182 String [] vhosts = context.getContextHandler().getVirtualHosts();
1183 if (vhosts==null || vhosts.length==0 || vhosts[0]==null)
1184 return vhost;
1185
1186 return vhosts[0];
1187 }
1188
1189
1190
1191
1192
1193
1194
1195 private static String canonicalize (String path)
1196 {
1197 if (path==null)
1198 return "";
1199
1200 return path.replace('/', '_').replace('.','_').replace('\\','_');
1201 }
1202 }