View Javadoc

1   /*
2    * $Id: PGPSecurityFilter.java 7963 2007-08-21 08:53:15Z dirk.olmes $
3    * --------------------------------------------------------------------------------------
4    * Copyright (c) MuleSource, Inc.  All rights reserved.  http://www.mulesource.com
5    *
6    * The software in this package is published under the terms of the CPAL v1.0
7    * license, a copy of which has been included with this distribution in the
8    * LICENSE.txt file.
9    */
10  
11  package org.mule.extras.pgp.filters;
12  
13  import org.mule.MuleManager;
14  import org.mule.config.i18n.CoreMessages;
15  import org.mule.extras.pgp.PGPAuthentication;
16  import org.mule.extras.pgp.PGPCryptInfo;
17  import org.mule.extras.pgp.PGPKeyRing;
18  import org.mule.extras.pgp.i18n.PGPMessages;
19  import org.mule.impl.MuleMessage;
20  import org.mule.impl.RequestContext;
21  import org.mule.impl.security.AbstractEndpointSecurityFilter;
22  import org.mule.umo.UMOEncryptionStrategy;
23  import org.mule.umo.UMOEvent;
24  import org.mule.umo.UMOMessage;
25  import org.mule.umo.lifecycle.InitialisationException;
26  import org.mule.umo.security.UMOAuthentication;
27  import org.mule.umo.security.UMOSecurityContext;
28  import org.mule.umo.security.UnauthorisedException;
29  import org.mule.umo.security.UnknownAuthenticationTypeException;
30  
31  import java.io.ByteArrayInputStream;
32  import java.util.Collection;
33  
34  import cryptix.message.LiteralMessage;
35  import cryptix.message.Message;
36  import cryptix.message.MessageFactory;
37  import cryptix.message.SignedMessage;
38  import cryptix.pki.KeyBundle;
39  import org.apache.commons.logging.Log;
40  import org.apache.commons.logging.LogFactory;
41  
42  public class PGPSecurityFilter extends AbstractEndpointSecurityFilter
43  {
44      /**
45       * logger used by this class
46       */
47      protected static final Log logger = LogFactory.getLog(PGPSecurityFilter.class);
48  
49      private UMOEncryptionStrategy strategy;
50  
51      private String strategyName;
52  
53      private boolean signRequired;
54  
55      private PGPKeyRing keyManager;
56  
57      /*
58       * (non-Javadoc)
59       * 
60       * @see org.mule.impl.security.AbstractEndpointSecurityFilter#authenticateInbound(org.mule.umo.UMOEvent)
61       */
62      protected void authenticateInbound(UMOEvent event)
63          throws SecurityException, UnauthorisedException, UnknownAuthenticationTypeException
64      {
65          UMOMessage message = event.getMessage();
66  
67          String userId = (String)getCredentialsAccessor().getCredentials(event);
68  
69          byte[] creds = null;
70  
71          try
72          {
73              creds = message.getPayloadAsBytes();
74              creds = strategy.decrypt(creds, null);
75          }
76          catch (Exception e1)
77          {
78              throw new UnauthorisedException(
79                  CoreMessages.failedToReadPayload(), event.getMessage(), e1);
80          }
81  
82          UMOAuthentication authResult;
83          UMOAuthentication umoAuthentication;
84  
85          try
86          {
87              umoAuthentication = new PGPAuthentication(userId, decodeMsgRaw(creds));
88          }
89          catch (Exception e1)
90          {
91              throw new UnauthorisedException(
92                  CoreMessages.failedToReadPayload(), event.getMessage(), e1);
93          }
94  
95          try
96          {
97              authResult = getSecurityManager().authenticate(umoAuthentication);
98          }
99          catch (Exception e)
100         {
101             // Authentication failed
102             if (logger.isDebugEnabled())
103             {
104                 logger.debug("Authentication request for user: " + userId + " failed: " + e.toString());
105             }
106 
107             throw new UnauthorisedException(CoreMessages.authFailedForUser(userId), event.getMessage(), e);
108         }
109 
110         // Authentication success
111         if (logger.isDebugEnabled())
112         {
113             logger.debug("Authentication success: " + authResult.toString());
114         }
115 
116         UMOSecurityContext context = getSecurityManager().createSecurityContext(authResult);
117         event.getSession().setSecurityContext(context);
118 
119         try
120         {
121             RequestContext.rewriteEvent(new MuleMessage(
122                 getUnencryptedMessageWithoutSignature((PGPAuthentication)authResult)));
123         }
124         catch (Exception e2)
125         {
126             throw new UnauthorisedException(event.getMessage(), context, event.getEndpoint(), this);
127         }
128     }
129 
130     private Message decodeMsgRaw(byte[] raw) throws Exception
131     {
132         MessageFactory mf = MessageFactory.getInstance("OpenPGP");
133 
134         ByteArrayInputStream in = new ByteArrayInputStream(raw);
135 
136         Collection msgs = mf.generateMessages(in);
137 
138         return (Message)msgs.iterator().next();
139     }
140 
141     private String getUnencryptedMessageWithoutSignature(PGPAuthentication auth) throws Exception
142     {
143         Message msg = (Message)auth.getCredentials();
144 
145         if (msg instanceof SignedMessage)
146         {
147             msg = ((SignedMessage)msg).getContents();
148         }
149 
150         if (msg instanceof LiteralMessage)
151         {
152             return ((LiteralMessage)msg).getTextData();
153         }
154         else
155         {
156             throw new Exception("Wrong data");
157         }
158     }
159 
160     /*
161      * (non-Javadoc)
162      * 
163      * @see org.mule.impl.security.AbstractEndpointSecurityFilter#authenticateOutbound(org.mule.umo.UMOEvent)
164      */
165     protected void authenticateOutbound(UMOEvent event) throws SecurityException, UnauthorisedException
166     {
167         logger.debug("authenticateOutbound:" + event.getId());
168 
169         if (!isAuthenticate())
170         {
171             return;
172         }
173 
174         UMOMessage message = event.getMessage();
175 
176         KeyBundle userKeyBundle = keyManager.getKeyBundle((String)getCredentialsAccessor().getCredentials(
177             event));
178 
179         PGPCryptInfo cryptInfo = new PGPCryptInfo(userKeyBundle, signRequired);
180 
181         byte[] msg = null;
182 
183         try
184         {
185             msg = message.getPayloadAsBytes();
186             msg = strategy.encrypt(msg, cryptInfo);
187         }
188         catch (Exception e1)
189         {
190             throw new UnauthorisedException(CoreMessages.failedToReadPayload(), event.getMessage(), e1);
191         }
192 
193         try
194         {
195             String mesg = new String(msg);
196             RequestContext.rewriteEvent(new MuleMessage(mesg));
197             logger.debug("Message:" + mesg);
198         }
199         catch (Exception e2)
200         {
201             throw new UnauthorisedException(event.getMessage(), event.getSession().getSecurityContext(),
202                 event.getEndpoint(), this);
203         }
204     }
205 
206     protected void doInitialise() throws InitialisationException
207     {
208         if (strategyName != null)
209         {
210             strategy = MuleManager.getInstance().getSecurityManager().getEncryptionStrategy(strategyName);
211         }
212 
213         if (strategy == null)
214         {
215             throw new InitialisationException(PGPMessages.encryptionStrategyNotSet(), this);
216         }
217     }
218 
219     public UMOEncryptionStrategy getStrategy()
220     {
221         return strategy;
222     }
223 
224     public void setStrategy(UMOEncryptionStrategy strategy)
225     {
226         this.strategy = strategy;
227     }
228 
229     public void setStrategyName(String name)
230     {
231         strategyName = name;
232     }
233 
234     public boolean isSignRequired()
235     {
236         return signRequired;
237     }
238 
239     public void setSignRequired(boolean signRequired)
240     {
241         this.signRequired = signRequired;
242     }
243 
244     public PGPKeyRing getKeyManager()
245     {
246         return keyManager;
247     }
248 
249     public void setKeyManager(PGPKeyRing keyManager)
250     {
251         this.keyManager = keyManager;
252     }
253 }