1 package pl.matsuo.core.web.scope;
2
3 import org.slf4j.Logger;
4 import org.slf4j.LoggerFactory;
5 import org.springframework.beans.factory.ObjectFactory;
6 import org.springframework.beans.factory.config.Scope;
7 import org.springframework.core.NamedThreadLocal;
8 import org.springframework.web.context.request.AbstractRequestAttributesScope;
9 import org.springframework.web.context.request.RequestAttributes;
10 import org.springframework.web.context.request.RequestContextHolder;
11
12 import java.util.HashMap;
13 import java.util.Map;
14
15
16
17
18
19
20 public class WideSessionScope extends AbstractRequestAttributesScope implements Scope {
21 private static final Logger logger = LoggerFactory.getLogger(WideSessionScope.class);
22
23
24 protected Map<String, ThreadLocal<Object>> objectHolders = new HashMap<>();
25
26
27 @Override
28 protected int getScope() {
29
30 return 13;
31 }
32
33
34 @Override
35 public String getConversationId() {
36 try {
37 return RequestContextHolder.currentRequestAttributes().getSessionId();
38 } catch (IllegalStateException e) {
39 logger.debug("outside web session");
40 e.printStackTrace();
41 return "non_web_";
42 }
43 }
44
45
46 @Override
47 public Object get(String name, ObjectFactory<?> objectFactory) {
48 try {
49 Object mutex = RequestContextHolder.currentRequestAttributes().getSessionMutex();
50 synchronized (mutex) {
51 return super.get(name, objectFactory);
52 }
53 } catch (IllegalStateException e) {
54 logger.debug("outside web session");
55 ThreadLocal<Object> objectHolder = objectHolders.get(name);
56 if (objectHolder == null) {
57 objectHolders.put(name, new NamedThreadLocal<>("wideScopeObjectHolder_" + name));
58 objectHolder = objectHolders.get(name);
59 }
60
61 if (objectHolder.get() == null) {
62 objectHolder.set(objectFactory.getObject());
63 }
64 return objectHolder.get();
65 }
66 }
67
68
69 @Override
70 public Object remove(String name) {
71 try {
72 Object mutex = RequestContextHolder.currentRequestAttributes().getSessionMutex();
73 synchronized (mutex) {
74 return super.remove(name);
75 }
76 } catch (IllegalStateException e) {
77 logger.debug("outside web session");
78 Object object = objectHolders.get(name).get();
79 objectHolders.get(name).set(null);
80 return object;
81 }
82 }
83
84
85 @Override
86 public void registerDestructionCallback(String name, Runnable callback) {
87 try {
88 logger.debug("outside web session");
89 RequestAttributes attributes = RequestContextHolder.currentRequestAttributes();
90 attributes.registerDestructionCallback(name, callback, getScope());
91 } catch (IllegalStateException e) {
92
93 }
94 }
95 }
96