1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.springframework.security.oauth.common.signature;
18
19 import org.springframework.security.authentication.encoding.PasswordEncoder;
20 import org.springframework.security.core.Authentication;
21 import org.springframework.security.core.context.SecurityContextHolder;
22 import static org.springframework.security.oauth.common.OAuthCodec.oauthEncode;
23
24 import javax.crypto.spec.SecretKeySpec;
25 import java.io.UnsupportedEncodingException;
26 import java.security.PrivateKey;
27 import java.security.PublicKey;
28 import java.security.cert.X509Certificate;
29
30
31
32
33
34
35 public class CoreOAuthSignatureMethodFactory implements OAuthSignatureMethodFactory {
36
37 private boolean supportPlainText = false;
38 private boolean supportHMAC_SHA1 = true;
39 private boolean supportRSA_SHA1 = true;
40 private PasswordEncoder plainTextPasswordEncoder;
41
42 public OAuthSignatureMethod getSignatureMethod(String methodName, SignatureSecret signatureSecret, String tokenSecret) throws UnsupportedSignatureMethodException {
43 if (supportPlainText && PlainTextSignatureMethod.SIGNATURE_NAME.equals(methodName)) {
44 if (!(signatureSecret instanceof SharedConsumerSecret)) {
45 throw new IllegalArgumentException("Invalid secret for signature method " + methodName + ". Expected a " +
46 SharedConsumerSecret.class.getName() + ", got " + (signatureSecret == null ? "null" : signatureSecret.getClass().getName()) + ".");
47 }
48
49 String consumerSecret = ((SharedConsumerSecret) signatureSecret).getConsumerSecret();
50 if (consumerSecret == null) {
51 consumerSecret = "";
52 }
53 if (tokenSecret == null) {
54 tokenSecret = "";
55 }
56
57 consumerSecret = oauthEncode(consumerSecret);
58 tokenSecret = oauthEncode(tokenSecret);
59
60 Object salt = null;
61 if (signatureSecret instanceof SaltedConsumerSecret) {
62 salt = ((SaltedConsumerSecret) signatureSecret).getSalt();
63 }
64
65 return new PlainTextSignatureMethod(oauthEncode(new StringBuilder(consumerSecret).append('&').append(tokenSecret).toString()), this.plainTextPasswordEncoder, salt);
66 }
67 else if (supportHMAC_SHA1 && HMAC_SHA1SignatureMethod.SIGNATURE_NAME.equals(methodName)) {
68 if (!(signatureSecret instanceof SharedConsumerSecret)) {
69 throw new IllegalArgumentException("Invalid secret for signature method " + methodName + ". Expected a " +
70 SharedConsumerSecret.class.getName() + ", got " + (signatureSecret == null ? "null" : signatureSecret.getClass().getName()) + ".");
71 }
72
73 String consumerSecret = ((SharedConsumerSecret) signatureSecret).getConsumerSecret();
74
75 if (consumerSecret == null) {
76 consumerSecret = "";
77 }
78 if (tokenSecret == null) {
79 tokenSecret = "";
80 }
81
82 consumerSecret = oauthEncode(consumerSecret);
83 tokenSecret = oauthEncode(tokenSecret);
84
85 byte[] keyBytes;
86 try {
87 keyBytes = new StringBuilder(consumerSecret).append('&').append(tokenSecret).toString().getBytes("UTF-8");
88 }
89 catch (UnsupportedEncodingException e) {
90 throw new RuntimeException(e.getMessage());
91 }
92 SecretKeySpec spec = new SecretKeySpec(keyBytes, HMAC_SHA1SignatureMethod.MAC_NAME);
93 return new HMAC_SHA1SignatureMethod(spec);
94 }
95 else if (supportRSA_SHA1 && RSA_SHA1SignatureMethod.SIGNATURE_NAME.equals(methodName)) {
96 if (signatureSecret instanceof RSAKeySecret) {
97 PublicKey publicKey = ((RSAKeySecret) signatureSecret).getPublicKey();
98 PrivateKey privateKey = ((RSAKeySecret) signatureSecret).getPrivateKey();
99 return new RSA_SHA1SignatureMethod(privateKey, publicKey);
100 }
101 else {
102 Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
103 if (authentication.getCredentials() instanceof X509Certificate) {
104 X509Certificate certificate = (X509Certificate) authentication.getCredentials();
105 if (certificate != null) {
106 return new RSA_SHA1SignatureMethod(certificate.getPublicKey());
107 }
108 }
109 }
110 }
111
112 throw new UnsupportedSignatureMethodException("Unsupported signature method: " + methodName);
113 }
114
115
116
117
118
119
120 public boolean isSupportPlainText() {
121 return supportPlainText;
122 }
123
124
125
126
127
128
129 public void setSupportPlainText(boolean supportPlainText) {
130 this.supportPlainText = supportPlainText;
131 }
132
133
134
135
136
137
138 public boolean isSupportHMAC_SHA1() {
139 return supportHMAC_SHA1;
140 }
141
142
143
144
145
146
147 public void setSupportHMAC_SHA1(boolean supportHMAC_SHA1) {
148 this.supportHMAC_SHA1 = supportHMAC_SHA1;
149 }
150
151
152
153
154
155
156 public boolean isSupportRSA_SHA1() {
157 return supportRSA_SHA1;
158 }
159
160
161
162
163
164
165 public void setSupportRSA_SHA1(boolean supportRSA_SHA1) {
166 this.supportRSA_SHA1 = supportRSA_SHA1;
167 }
168
169
170
171
172
173
174 public PasswordEncoder getPlainTextPasswordEncoder() {
175 return plainTextPasswordEncoder;
176 }
177
178
179
180
181
182
183 public void setPlainTextPasswordEncoder(PasswordEncoder plainTextPasswordEncoder) {
184 this.plainTextPasswordEncoder = plainTextPasswordEncoder;
185 }
186 }