Clover Coverage Report - Atlassian Trusted Apps(Aggregated)
Coverage timestamp: Tue Jun 9 2009 19:34:44 CDT
59   142   15   14.75
20   119   0.25   4
4     3.75  
1    
 
 
  TrustedApplicationFilterAuthenticator       Line # 21 59 15 97.6% 0.97590363
 
  (23)
 
1    package com.atlassian.security.auth.trustedapps.filter;
2   
3    import com.atlassian.security.auth.trustedapps.ApplicationCertificate;
4    import com.atlassian.security.auth.trustedapps.DefaultEncryptedCertificate;
5    import com.atlassian.security.auth.trustedapps.InvalidCertificateException;
6    import com.atlassian.security.auth.trustedapps.TransportErrorMessage;
7    import com.atlassian.security.auth.trustedapps.TrustedApplication;
8    import com.atlassian.security.auth.trustedapps.TrustedApplicationUtils;
9    import com.atlassian.security.auth.trustedapps.TrustedApplicationsManager;
10    import com.atlassian.security.auth.trustedapps.UserResolver;
11    import org.slf4j.Logger;
12    import org.slf4j.LoggerFactory;
13   
14    import javax.servlet.http.HttpServletRequest;
15    import javax.servlet.http.HttpServletResponse;
16    import java.security.Principal;
17   
18    /**
19    *
20    */
 
21    public class TrustedApplicationFilterAuthenticator implements Authenticator
22    {
23    private static final Logger log = LoggerFactory.getLogger(TrustedApplicationFilterAuthenticator.class);
24   
25    final TrustedApplicationsManager appManager;
26    final UserResolver resolver;
27    final AuthenticationController authenticationController;
28   
 
29  23 toggle public TrustedApplicationFilterAuthenticator(TrustedApplicationsManager appManager, UserResolver resolver, AuthenticationController authenticationController)
30    {
31  23 this.appManager = appManager;
32  23 this.resolver = resolver;
33  23 this.authenticationController = authenticationController;
34    }
35   
 
36  23 toggle public Result authenticate(HttpServletRequest request, HttpServletResponse response)
37    {
38  23 final String certStr = request.getHeader(TrustedApplicationUtils.Header.Request.CERTIFICATE);
39  23 if (isBlank(certStr))
40    {
41  1 return new Result.NoAttempt();
42    }
43   
44  22 final String id = request.getHeader(TrustedApplicationUtils.Header.Request.ID);
45  22 if (isBlank(id))
46    {
47  1 final Result.Error result = new Result.Error(new TransportErrorMessage.ApplicationIdNotFoundInRequest());
48  1 setFailureHeader(response, result.getMessage());
49  1 return result;
50    }
51   
52  21 final String key = request.getHeader(TrustedApplicationUtils.Header.Request.SECRET_KEY);
53  21 if (isBlank(key))
54    {
55  1 final Result.Error result = new Result.Error(new TransportErrorMessage.SecretKeyNotFoundInRequest());
56  1 setFailureHeader(response, result.getMessage());
57  1 return result;
58    }
59   
60  20 final String magicNumber = request.getHeader(TrustedApplicationUtils.Header.Request.MAGIC);
61    // magic number validation is only done from protocol version 2, version 1 had no version header
62  20 final String version = request.getHeader(TrustedApplicationUtils.Header.Request.VERSION);
63  20 final Integer protocolVersion;
64  20 try
65    {
66  20 protocolVersion = (!isBlank(version)) ? new Integer(version) : null;
67    }
68    catch (NumberFormatException e)
69    {
70  1 final Result.Error result = new Result.Error(new TransportErrorMessage.BadProtocolVersion(version));
71  1 setFailureHeader(response, result.getMessage());
72  1 return result;
73    }
74   
75    // note, this code only handles non-null version - doesn't differentiate between 1 & 2
76  19 if (protocolVersion != null)
77    {
78  16 if (isBlank(magicNumber))
79    {
80  1 final Result.Error result = new Result.Error(new TransportErrorMessage.MagicNumberNotFoundInRequest());
81  1 setFailureHeader(response, result.getMessage());
82  1 return result;
83    }
84    }
85   
86  18 TrustedApplication app = appManager.getTrustedApplication(id);
87  18 if (app == null)
88    {
89  2 final Result.Failure result = new Result.Failure(new TransportErrorMessage.ApplicationUnknown(id));
90  2 setFailureHeader(response, result.getMessage());
91  2 return result;
92    }
93   
94  16 final ApplicationCertificate certificate;
95  16 try
96    {
97  16 certificate = app.decode(new DefaultEncryptedCertificate(id, key, certStr, protocolVersion, magicNumber), request);
98    }
99    catch (InvalidCertificateException ex)
100    {
101  10 log.warn("Failed to login trusted application: " + app.getID() + " due to: " + ex);
102    // debug for stacktrace, no need for isDebugEnabled check as there is no string concatenation
103  10 log.debug("Failed to login trusted application cause", ex);
104  10 final Result.Error result = new Result.Error(ex.getTransportErrorMessage());
105  10 setFailureHeader(response, result.getMessage());
106  10 return result;
107    }
108  6 final Principal user = resolver.resolve(certificate);
109  6 if (user == null)
110    {
111  1 log.warn("User '" + certificate.getUserName() + "' referenced by trusted application: '" + app.getID() + "' is not found.");
112  1 final Result.Failure result = new Result.Failure(new TransportErrorMessage.UserUnknown(certificate.getUserName()));
113  1 setFailureHeader(response, result.getMessage());
114  1 return result;
115    }
116  5 else if (!authenticationController.canLogin(user, request))
117    {
118    // user exists but is not allowed to login
119  1 log.warn("User '" + certificate.getUserName() + "' referenced by trusted application: '" + app.getID() + "' cannot login.");
120  1 final Result.Failure result = new Result.Failure(new TransportErrorMessage.PermissionDenied());
121  1 setFailureHeader(response, result.getMessage());
122  1 return result;
123    }
124   
125  4 return new Result.Success(user);
126    }
127   
 
128  18 toggle private static void setFailureHeader(HttpServletResponse response, String message)
129    {
130  18 response.setHeader(TrustedApplicationUtils.Header.Response.STATUS, TrustedApplicationsFilter.Status.ERROR);
131  18 response.addHeader(TrustedApplicationUtils.Header.Response.ERROR, message);
132  18 if (log.isInfoEnabled())
133    {
134  0 log.info(message, new RuntimeException(message));
135    }
136    }
137   
 
138  102 toggle private static boolean isBlank(String input)
139    {
140  102 return (input == null) || input.trim().length() == 0;
141    }
142    }