1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 package org.apache.struts2.util;
23
24 import java.math.BigInteger;
25 import java.util.Map;
26 import java.util.Random;
27
28 import com.opensymphony.xwork2.ActionContext;
29 import com.opensymphony.xwork2.util.LocalizedTextUtil;
30 import com.opensymphony.xwork2.util.logging.Logger;
31 import com.opensymphony.xwork2.util.logging.LoggerFactory;
32
33 /***
34 * TokenHelper
35 *
36 */
37 public class TokenHelper {
38
39 /***
40 * The default name to map the token value
41 */
42 public static final String DEFAULT_TOKEN_NAME = "struts.token";
43
44 /***
45 * The name of the field which will hold the token name
46 */
47 public static final String TOKEN_NAME_FIELD = "struts.token.name";
48 private static final Logger LOG = LoggerFactory.getLogger(TokenHelper.class);
49 private static final Random RANDOM = new Random();
50
51
52 /***
53 * Sets a transaction token into the session using the default token name.
54 *
55 * @return the token string
56 */
57 public static String setToken() {
58 return setToken(DEFAULT_TOKEN_NAME);
59 }
60
61 /***
62 * Sets a transaction token into the session using the provided token name.
63 *
64 * @param tokenName the name to store into the session with the token as the value
65 * @return the token string
66 */
67 public static String setToken(String tokenName) {
68 Map session = ActionContext.getContext().getSession();
69 String token = generateGUID();
70 try {
71 session.put(tokenName, token);
72 }
73 catch(IllegalStateException e) {
74
75 String msg = "Error creating HttpSession due response is commited to client. You can use the CreateSessionInterceptor or create the HttpSession from your action before the result is rendered to the client: " + e.getMessage();
76 LOG.error(msg, e);
77 throw new IllegalArgumentException(msg);
78 }
79
80 return token;
81 }
82
83
84 /***
85 * Gets a transaction token into the session using the default token name.
86 *
87 * @return token
88 */
89 public static String getToken() {
90 return getToken(DEFAULT_TOKEN_NAME);
91 }
92
93 /***
94 * Gets the Token value from the params in the ServletActionContext using the given name
95 *
96 * @param tokenName the name of the parameter which holds the token value
97 * @return the token String or null, if the token could not be found
98 */
99 public static String getToken(String tokenName) {
100 if (tokenName == null ) {
101 return null;
102 }
103 Map params = ActionContext.getContext().getParameters();
104 String[] tokens = (String[]) params.get(tokenName);
105 String token;
106
107 if ((tokens == null) || (tokens.length < 1)) {
108 LOG.warn("Could not find token mapped to token name " + tokenName);
109
110 return null;
111 }
112
113 token = tokens[0];
114
115 return token;
116 }
117
118 /***
119 * Gets the token name from the Parameters in the ServletActionContext
120 *
121 * @return the token name found in the params, or null if it could not be found
122 */
123 public static String getTokenName() {
124 Map params = ActionContext.getContext().getParameters();
125
126 if (!params.containsKey(TOKEN_NAME_FIELD)) {
127 LOG.warn("Could not find token name in params.");
128
129 return null;
130 }
131
132 String[] tokenNames = (String[]) params.get(TOKEN_NAME_FIELD);
133 String tokenName;
134
135 if ((tokenNames == null) || (tokenNames.length < 1)) {
136 LOG.warn("Got a null or empty token name.");
137
138 return null;
139 }
140
141 tokenName = tokenNames[0];
142
143 return tokenName;
144 }
145
146 /***
147 * Checks for a valid transaction token in the current request params. If a valid token is found, it is
148 * removed so the it is not valid again.
149 *
150 * @return false if there was no token set into the params (check by looking for {@link #TOKEN_NAME_FIELD}), true if a valid token is found
151 */
152 public static boolean validToken() {
153 String tokenName = getTokenName();
154
155 if (tokenName == null) {
156 if (LOG.isDebugEnabled())
157 LOG.debug("no token name found -> Invalid token ");
158 return false;
159 }
160
161 String token = getToken(tokenName);
162
163 if (token == null) {
164 if (LOG.isDebugEnabled())
165 LOG.debug("no token found for token name "+tokenName+" -> Invalid token ");
166 return false;
167 }
168
169 Map session = ActionContext.getContext().getSession();
170 String sessionToken = (String) session.get(tokenName);
171
172 if (!token.equals(sessionToken)) {
173 LOG.warn(LocalizedTextUtil.findText(TokenHelper.class, "struts.internal.invalid.token", ActionContext.getContext().getLocale(), "Form token {0} does not match the session token {1}.", new Object[]{
174 token, sessionToken
175 }));
176
177 return false;
178 }
179
180
181 session.remove(tokenName);
182
183 return true;
184 }
185
186 public static String generateGUID() {
187 return new BigInteger(165, RANDOM).toString(36).toUpperCase();
188 }
189 }