001/** 002 * GRANITE DATA SERVICES 003 * Copyright (C) 2006-2013 GRANITE DATA SERVICES S.A.S. 004 * 005 * This file is part of the Granite Data Services Platform. 006 * 007 * Granite Data Services is free software; you can redistribute it and/or 008 * modify it under the terms of the GNU Lesser General Public 009 * License as published by the Free Software Foundation; either 010 * version 2.1 of the License, or (at your option) any later version. 011 * 012 * Granite Data Services is distributed in the hope that it will be useful, 013 * but WITHOUT ANY WARRANTY; without even the implied warranty of 014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser 015 * General Public License for more details. 016 * 017 * You should have received a copy of the GNU Lesser General Public 018 * License along with this library; if not, write to the Free Software 019 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, 020 * USA, or see <http://www.gnu.org/licenses/>. 021 */ 022package org.granite.messaging.amf.process; 023 024import java.util.Date; 025 026import org.granite.config.GraniteConfig; 027import org.granite.context.GraniteContext; 028import org.granite.logging.Logger; 029import org.granite.messaging.service.ServiceException; 030import org.granite.messaging.service.ServiceFactory; 031import org.granite.messaging.service.ServiceInvoker; 032import org.granite.messaging.service.security.SecurityService; 033import org.granite.messaging.service.security.SecurityServiceException; 034import org.granite.messaging.webapp.ServletGraniteContext; 035import org.granite.util.UUIDUtil; 036 037import flex.messaging.messages.AcknowledgeMessage; 038import flex.messaging.messages.CommandMessage; 039import flex.messaging.messages.ErrorMessage; 040import flex.messaging.messages.Message; 041import flex.messaging.messages.RemotingMessage; 042 043/** 044 * @author Franck WOLFF 045 */ 046public abstract class AMF3MessageProcessor { 047 048 private static final Logger log = Logger.getLogger(AMF3MessageProcessor.class); 049 050 public static Message process(Message request) { 051 GraniteContext context = GraniteContext.getCurrentInstance(); 052 AMF3MessageInterceptor interceptor = context.getGraniteConfig().getAmf3MessageInterceptor(); 053 054 Message response = null; 055 try { 056 if (interceptor != null) 057 interceptor.before(request); 058 059 if (request instanceof RemotingMessage) 060 response = processRemotingMessage((RemotingMessage)request); 061 else if (request instanceof CommandMessage) 062 response = processCommandMessage((CommandMessage)request); 063 else 064 throw new IllegalArgumentException("Unknown request message type: " + request); 065 } 066 finally { 067 if (interceptor != null) 068 interceptor.after(request, response); 069 } 070 071 if (context.getSessionId() != null) { 072 response.setHeader("org.granite.sessionId", context.getSessionId()); 073 if (((ServletGraniteContext)context).getSession(false) != null) { 074 long serverTime = new Date().getTime(); 075 ((ServletGraniteContext)context).getSession().setAttribute(GraniteContext.SESSION_LAST_ACCESSED_TIME_KEY, serverTime); 076 response.setHeader("org.granite.time", serverTime); 077 response.setHeader("org.granite.sessionExp", ((ServletGraniteContext)context).getSession().getMaxInactiveInterval()); 078 } 079 } 080 081 return response; 082 } 083 084 public static Message processCommandMessage(CommandMessage request) { 085 086 log.debug(">> Processing AMF3 request:\n%s", request); 087 088 Message response = null; 089 if (request.isSecurityOperation()) { 090 GraniteContext context = GraniteContext.getCurrentInstance(); 091 GraniteConfig config = context.getGraniteConfig(); 092 093 if (!config.hasSecurityService()) 094 log.warn("Ignored security operation (no security settings in granite-config.xml): %s", request); 095 else { 096 SecurityService securityService = config.getSecurityService(); 097 try { 098 if (request.isLoginOperation()) 099 securityService.login(request.getBody(), (String)request.getHeader(Message.CREDENTIALS_CHARSET_HEADER)); 100 else if (request.isLogoutOperation()) 101 securityService.logout(); 102 else 103 log.warn("Unknown security operation: %s", request); 104 } catch (Exception e) { 105 if (e instanceof SecurityServiceException) { 106 securityService.handleSecurityException((SecurityServiceException)e); 107 log.debug(e, "Could not process security operation: %s", request); 108 } 109 else 110 log.error(e, "Could not process security operation: %s", request); 111 response = new ErrorMessage(request, e); 112 } 113 } 114 } 115 116 if (response == null) { 117 response = new AcknowledgeMessage(request); 118 // For SDK 2.0.1_Hotfix2. 119 if (request.isSecurityOperation()) 120 response.setBody("success"); 121 } 122 123 // For SDK 2.0.1_Hotfix2. 124 if ("nil".equals(request.getHeader(Message.DS_ID_HEADER))) 125 response.getHeaders().put(Message.DS_ID_HEADER, UUIDUtil.randomUUID()); 126 127 log.debug("<< Returning AMF3 response:\n%s", response); 128 129 return response; 130 } 131 132 public static Message processRemotingMessage(RemotingMessage request) { 133 134 log.debug(">> Processing AMF3 request:\n%s", request); 135 136 Message response = null; 137 try { 138 // Execute method on service. 139 ServiceFactory factory = ServiceFactory.getFactoryInstance(request); 140 ServiceInvoker<?> service = factory.getServiceInstance(request); 141 Object result = service.invoke(request); 142 143 response = new AcknowledgeMessage(request); 144 response.setBody(result); 145 } catch (ServiceException e) { 146 log.debug(e, "Could not process remoting message: %s", request); 147 response = new ErrorMessage(request, e); 148 } 149 150 log.debug("<< Returning AMF3 response:\n%s", response); 151 152 return response; 153 } 154}