Package com.sun.enterprise.ee.web.sessmgmt

Source Code of com.sun.enterprise.ee.web.sessmgmt.InputPipeWrapper$ReceivedMessageWrapper

/*
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright 1997-2007 Sun Microsystems, Inc. All rights reserved.
*
* The contents of this file are subject to the terms of either the GNU
* General Public License Version 2 only ("GPL") or the Common Development
* and Distribution License("CDDL") (collectively, the "License").  You
* may not use this file except in compliance with the License. You can obtain
* a copy of the License at https://glassfish.dev.java.net/public/CDDL+GPL.html
* or glassfish/bootstrap/legal/LICENSE.txt.  See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each
* file and include the License file at glassfish/bootstrap/legal/LICENSE.txt.
* Sun designates this particular file as subject to the "Classpath" exception
* as provided by Sun in the GPL Version 2 section of the License file that
* accompanied this code.  If applicable, add the following below the License
* Header, with the fields enclosed by brackets [] replaced by your own
* identifying information: "Portions Copyrighted [year]
* [name of copyright owner]"
*
* Contributor(s):
*
* If you wish your version of this file to be governed by only the CDDL or
* only the GPL Version 2, indicate your decision by adding "[Contributor]
* elects to include this software in this distribution under the [CDDL or GPL
* Version 2] license."  If you don't indicate a single choice of license, a
* recipient has the option to distribute your version of this file under
* either the CDDL, the GPL Version 2 or to extend the choice of license to
* its licensees as provided above.  However, if you add GPL Version 2 code
* and therefore, elected the GPL Version 2 license, then the option applies
* only if the new code is made subject to such option by the copyright
* holder.
*/
/*
*InputPipeWrapper.java
*
* Created on March 22, 2006, 12:02 PM
*
*/

package com.sun.enterprise.ee.web.sessmgmt;

import java.io.IOException;
import java.security.AccessController;
import java.util.logging.Logger;
import java.util.logging.Level;
import com.sun.logging.LogDomains;

import com.sun.enterprise.web.ServerConfigLookup;

import org.apache.catalina.Globals;

import java.util.List;

import net.jxta.document.AdvertisementFactory;
import net.jxta.document.StructuredDocumentFactory;
import net.jxta.document.XMLDocument;
import net.jxta.endpoint.Message;
import net.jxta.endpoint.MessageElement;
import net.jxta.pipe.InputPipe;
import net.jxta.pipe.PipeMsgEvent;
import net.jxta.pipe.PipeMsgListener;
import net.jxta.protocol.RouteAdvertisement;

/**
*
* @author Larry White
*/
public class InputPipeWrapper extends AbstractPipeWrapper implements PipeMsgListener {
   
    private final static String InstanceNameMessage
        = ReplicationState.InstanceNameMessage;
    private final static String ReadyMessage
        = ReplicationState.ReadyMessage;   
    private final static String MESSAGE_MODE =
        ReplicationState.MESSAGE_MODE;
    private final static String BULK_MESSAGE_MODE =
        ReplicationState.BULK_MESSAGE_MODE;   
    private final static String MESSAGE_ID
        = ReplicationState.MESSAGE_ID;   
    private final static String MESSAGE_COMMAND
        = ReplicationState.MESSAGE_COMMAND;
    private final static String MESSAGE_BROADCAST_QUERY
        = ReplicationState.MESSAGE_BROADCAST_QUERY;
    private final static String RETURN_BROADCAST_MSG_COMMAND
        = ReplicationState.RETURN_BROADCAST_MSG_COMMAND;
    private final static String MESSAGE_BROADCAST_LOAD_RECEIVED
        = ReplicationState.MESSAGE_BROADCAST_LOAD_RECEIVED;
    private final static String MESSAGE_READY
        = ReplicationState.MESSAGE_READY;
    private final static Level TRACE_LEVEL = Level.FINE;
    public final static String MESSAGE_SEND_START_TIME =
        ReplicationState.MESSAGE_SEND_START_TIME;
   
    private static final Logger _logger = LogDomains.getLogger(LogDomains.WEB_LOGGER);
    private static final Logger _pipelogger = ReplicationUtil.getPipeLogger();
      
    /**
     * Creates a new instance of InputPipeWrapper
     */
    public InputPipeWrapper() {
    }
   
    /** Creates a new instance of InputPipeWrapper */
    public InputPipeWrapper(String name, InputPipe pipe) {
        _name = name;
        _pipe = pipe;
    }
   
    /**
     *  This is the PipeListener interface. Expect a call to this method
     *  When a message is received.
     *  when we get a message, print out the message on the console
     *  all incoming messages must have an InstanceNameMessage element
     *@param  event  message event
     */
    public void pipeMsgEvent(PipeMsgEvent event) {

        Message msg = null;
        try {
            // grab the message from the event
            msg = event.getMessage();
            //displayKeyMessageElements(msg);
          
            if (msg == null) {
                 if (_logger.isLoggable(Level.FINEST)) {
                    _logger.finest("Received an empty message, returning");
                 }               
                return;
            }

            ReplicationUtil repUtil = ReplicationUtil.createReplicationUtil();

            if (repUtil.isInstanceLoadBalancedByCLB()) {
                MessageProcessor.getInstance().pipeMsgEvent(event, null);
                return;
            }
            // get the message element named InstanceNameMessage

            MessageElement instanceNameMsgElement =
                msg.getMessageElement(InstanceNameMessage, InstanceNameMessage);
            //ignore broadcasts from yourself
            String returnInstance = null;
            if(instanceNameMsgElement != null) {
                returnInstance = instanceNameMsgElement.toString();
                if (_logger.isLoggable(Level.FINE)) {
                    _logger.fine("InputPipeWrapper:incoming propagated msg from: " + returnInstance);
                }               
            }
            if(returnInstance.equalsIgnoreCase(getInstanceName())) {
                return;
            }
           
            MessageElement readyMsgElement = msg.getMessageElement(ReadyMessage, ReadyMessage);
            if(readyMsgElement != null) {
                try {
                    Thread.currentThread().sleep(2000L);
                } catch(InterruptedException ex) {}               
                if (_pipelogger.isLoggable(Level.FINE)) {
                    _pipelogger.fine("readyMsgElement=" + readyMsgElement.toString() + " from: " + returnInstance)
                }
                JoinNotificationEventHandler.checkAndDoJoinFor(returnInstance);
            }
           
            MessageElement bulkMsgElement = msg.getMessageElement(BULK_MESSAGE_MODE, BULK_MESSAGE_MODE);
            if (bulkMsgElement != null) {
                processBulkMessage(msg, bulkMsgElement);
                return;
            }           
                  
            MessageElement idMsgElement = msg.getMessageElement(MESSAGE_ID, MESSAGE_ID);
            if(idMsgElement != null) {
                if (_logger.isLoggable(Level.FINE)) {
                    _logger.fine("idMsgElement=" + idMsgElement.toString());
                }
            }
            MessageElement commandMsgElement =
                msg.getMessageElement(MESSAGE_COMMAND, MESSAGE_COMMAND);            
            if(commandMsgElement != null) {
                String theCommand = commandMsgElement.toString();
                if(isBroadcastMethod(theCommand)) {
                    //processQueryMessage(msg, idMsgElement, returnInstance);
                    ReplicationMessageRouter receiver = getRouter();
                    ReplicationState state = createReplicationState(msg);
                    processQueryState(state, receiver);
                }               
            }

        } catch (Exception e) {
            if (_logger.isLoggable(Level.FINEST)) {
                _logger.log(Level.FINEST, "caught exception", e);
            }            
            return;
        }
    }

    class ReceivedMessageWrapper
        implements Runnable {

        ReplicationMessageRouter receiver;
        ReplicationState state;

        ReceivedMessageWrapper(ReplicationMessageRouter receiver, ReplicationState state) {
            this.receiver = receiver;
            this.state = state;
        }

        public void run() {
            try {
                //handleReceivedMessage(msg);
                receiver.processQueryMessage(state, state.getInstanceName());              
            } catch (Exception ex) {
                if (_logger.isLoggable(Level.FINE)) {
                    _logger.log(Level.FINE, "caught exception", ex);
                }            
            }
        }
    }

    private ReplicationMessageRouter getRouter() {
        ReplicationMessageRouter receiver = null;
        if (Globals.IS_SECURITY_ENABLED) {
            receiver = (ReplicationMessageRouter)
                AccessController.doPrivileged(
                    new PrivilegedGetReplicationMessageRouter());
        } else {
            receiver = ReplicationMessageRouter.createInstance();
        }
        return receiver;
    }
   
    private boolean isBroadcastMethod(String theCommand) {
        ReplicationMessageRouter receiver = getRouter();
        return receiver.isBroadcastMethod(theCommand);       
    }

    private boolean isExpensiveMethod(String theCommand) {
        ReplicationMessageRouter receiver = getRouter();
        return receiver.isExpensiveMethod(theCommand);
    }
   
    private void displayKeyMessageElements(Message msg) {
        if (_logger.isLoggable(Level.FINE)) {
            _logger.fine("PropagatedPipeWrapper>>pipeMsgEvent:msg=" + msg);
        }
        MessageElement instanceNameMsgElement =
            msg.getMessageElement(InstanceNameMessage, InstanceNameMessage);
        String returnInstance = null;
        if(instanceNameMsgElement != null) {
            returnInstance = instanceNameMsgElement.toString();
            if (_logger.isLoggable(Level.FINE) && !isMessageFromYourself(returnInstance)) {
                _logger.fine("PropagatedPipeWrapper>>pipeMsgEvent:fromInstance=" + returnInstance);
            }
        }
       
        MessageElement idMsgElement = msg.getMessageElement(MESSAGE_ID, MESSAGE_ID);
        if(idMsgElement != null  && _logger.isLoggable(Level.FINE)) {
            _logger.fine("idMsgElement=" + idMsgElement.toString());
        }
       
        MessageElement commandMsgElement =
            msg.getMessageElement(MESSAGE_COMMAND, MESSAGE_COMMAND);            
        if(commandMsgElement != null) {
            String theCommand = commandMsgElement.toString();
            if (_logger.isLoggable(Level.FINE)) {
                _logger.fine("incoming msg to broadcast pipe:command=" + theCommand);
             }
        }        
    }
   
    private void processQueryMessage(Message msg, MessageElement idMsgElement, String returnInstance) {
        if (_logger.isLoggable(Level.FINER)) {
            _logger.entering("InputPipeWrapper", "processQueryMessage", new Object[] { msg, idMsgElement, returnInstance});
        }       
        if (idMsgElement.toString() == null) {
            if (_logger.isLoggable(Level.FINE)) {
                _logger.fine("null id msg received");
            }
            return;
        }
        ReplicationState state = this.createReplicationState(msg);

        ReplicationMessageRouter receiver = getRouter();
        receiver.processQueryMessage(state, returnInstance);       
      
    }
   
    private ReplicationState     createReplicationState(Message msg) {
        ReplicationState result
            = ReplicationState.createBroadcastReplicationState(msg);
        //adding route advertisment to this input query state
        RouteAdvertisement routeAdv = getRouteAdvertisement(msg);
        result.setRouteAdvertisement(routeAdv);
        return result;
    }

    private void addRoutesTo(List<ReplicationState>states, Message msg) {
        RouteAdvertisement routeAdv = getRouteAdvertisement(msg);
        for(int i=0; i<states.size(); i++) {
            ReplicationState nextState = states.get(i);
            nextState.setRouteAdvertisement(routeAdv);
        }
    }
   
    //begin unicast code
   
    private static final String NAMESPACE = ReplicationState.NAMESPACE;
    private static final String ROUTEADV = ReplicationState.ROUTEADV;
   
    RouteAdvertisement getRouteAdvertisement(Message msg) {
        RouteAdvertisement routeAdv = null;
        MessageElement routeElement = msg.getMessageElement(NAMESPACE, ROUTEADV);
        if(routeElement != null) {
            try {
                XMLDocument asDoc = (XMLDocument) StructuredDocumentFactory.newStructuredDocument(
                        routeElement.getMimeType(), routeElement.getStream());
                routeAdv = (RouteAdvertisement)
                        AdvertisementFactory.newAdvertisement(asDoc);
            } catch (IOException io) {
                io.printStackTrace();
            }
        }
        return routeAdv;
    }
   
    //end unicast code
   
    //begin bulk message handling
    private void processBulkMessage(Message msg, MessageElement idMsgElement) {
        if (_logger.isLoggable(Level.FINE)) {
            _logger.log(Level.FINE, ">>InputPipeWrapper:  processBulkMessage...");
        }
        //_logger.log(Level.INFO, ">>InputPipeWrapper:  processBulkMessage...");
        printMessageReceiptStats(msg);
        ReplicationMessageRouter receiver = getRouter();
       
        //check if this is a return bulk message and act accordingly
        //System.out.println("<<processBulkMessage:isVoidReturnMessage=" + ReplicationState.isVoidMethodReturnMessage(msg));
        //System.out.println("<<processBulkMessage:isAckRequiredForMessage=" + ReplicationState.isAckRequiredForMessage(msg));
        //System.out.println("<<processBulkMessage:isResponseMessage=" + ReplicationState.isResponseMessage(msg));
        /*
         * no acks here so leaving this out
        if(!ReplicationState.isAckRequiredForMessage(msg)
            && !ReplicationState.isVoidMethodReturnMessage(msg)
            && ReplicationState.isResponseMessage(msg)) {
            List<String> ackIds = ReplicationState.extractAckIdsListFromMessage(msg);
            //iterate and deliver acks to each id in ackIds list and return
            processAcks(ackIds, receiver);
            return;
        }
         */
            
        List<ReplicationState> states = ReplicationState.extractBulkReplicationStatesFromMessage(msg);
        addRoutesTo(states, msg);
       
        //send ack if required  FIXME: remove after testing not sending any acks here
        //this.checkSendImmediateBulkAck(msg, states);
       
        //_logger.log(Level.INFO, ">>InputPipeWrapper:  states size = " + states.size());       
        for (ReplicationState state : states) {
            if (_logger.isLoggable(TRACE_LEVEL)) {
                _logger.log(TRACE_LEVEL, "<<InputPipeWrapper:  receiving id: " + state.getId() + "[ver:" + state.getVersion() + "]");
                _logger.log(TRACE_LEVEL, "<<InputPipeWrapper:  receiving nextState isResponse " + state.isResponseState() + " state = " + state);
            }
            processQueryState(state, receiver);
        }
        if (_logger.isLoggable(Level.FINE)) {
            _logger.log(Level.FINE, "<<InputPipeWrapper:  processBulkMessage complete...");
        }
    }

    private void processQueryState(ReplicationState state, ReplicationMessageRouter receiver) {
        if(state.isResponseState()) {
            if(_logger.isLoggable(Level.FINE)) {
                _logger.fine("InputPipeWrapper:response command = " + state.getCommand());
            }
            processQueryResponse(state, receiver);
        } else {
            processQueryNonResponse(state, receiver);
        }
    }
   
    private void processQueryResponse(ReplicationState state, ReplicationMessageRouter receiver) {
        if(state.getCommand() != null && state.getCommand().equalsIgnoreCase("unicastResponse")) {
            receiver.processUnicastQueryResponse(state);
        } else {
            //this is a load response which gets processed quickly
            receiver.processQueryResponse(state);
        }
    }

    private void processQueryNonResponse(ReplicationState state, ReplicationMessageRouter receiver) {
        //not a response - only use separate thread for expensive commands
        if(isExpensiveMethod(state.getCommand())) {
            Runnable r = new ReceivedMessageWrapper(receiver, state);
            JxtaReplicationSender.executeTask(r);
        } else {
            receiver.processQueryMessage(state, state.getInstanceName());
        }
    }
   
    private void printMessageReceiptStats(Message receivedMessage) {
        if(!this.getReplicationMeasurementEnabled()) {
            return;
        }
        int measurementInterval = this.getReplicationMeasurementInterval();
        long id = -1L;
        MessageElement idMsgElement =
            receivedMessage.getMessageElement(MESSAGE_ID, MESSAGE_ID);
        if(idMsgElement != null) {
            id = (Long.decode(idMsgElement.toString())).longValue();
            //System.out.println("messageReceived: bulkId = " + id);
        }
        if(id % measurementInterval != 0) {
            return;
        }
        //get send start time for measurements
        long sendStartTime = -1L;
        MessageElement sendStartMsgElement =
            receivedMessage.getMessageElement(MESSAGE_SEND_START_TIME, MESSAGE_SEND_START_TIME);
        if(sendStartMsgElement != null) {
            sendStartTime =
                (Long.decode(sendStartMsgElement.toString())).longValue();
            if(sendStartTime > 0L) {
                //System.out.println("message receipt time: " + (System.currentTimeMillis() - sendStartTime));
            }
        }
        _logger.log(Level.INFO, "messageReceiptSucceeded: bulkId = " + id + " receiptTime = "
            + (System.currentTimeMillis() - sendStartTime) + " from partner: " + getPartnerInstanceName());      
    }
   
   
    Boolean _replicationMeasurementEnabled = null;
    private boolean getReplicationMeasurementEnabled() {
        if(_replicationMeasurementEnabled == null) {
            ServerConfigLookup lookup = new ServerConfigLookup();
            _replicationMeasurementEnabled
                = new Boolean(lookup.getReplicationMeasurementEnabledFromConfig());                       
        }
        return _replicationMeasurementEnabled.booleanValue();
    }

    int _replicationMeasurementInterval = -1;
    private int getReplicationMeasurementInterval() {
        if(_replicationMeasurementInterval == -1) {
            ServerConfigLookup lookup = new ServerConfigLookup();
            _replicationMeasurementInterval
                = lookup.getReplicationMeasurementIntervalFromConfig();                       
        }
        return _replicationMeasurementInterval;
    }     
   
    private void processAcks(List<String> acksList, ReplicationMessageRouter receiver) {
        //_logger.log(Level.INFO, ">>InputPipeWrapper:processAcks:  acksList size = " + acksList.size());
        for(int i=0; i<acksList.size(); i++) {
            //_logger.log(Level.INFO,"processAcks:nextIdToAck:" + acksList.get(i));
            ReplicationState nextState = new ReplicationState(acksList.get(i));
            receiver.processResponse(nextState);
        }
    }
      
    //end bulk message handling
   
    public void cleanup() {

        if (_pipelogger.isLoggable(Level.FINER)) {
            _pipelogger.entering("InputPipeWrapper", "cleanup", _pipe);
        }
        if(_pipe != null) {
            _pipe.close();
            if (_pipelogger.isLoggable(Level.FINE)) {
                _pipelogger.fine("InputPipeWrapper>>_pipe.close() called for " + _name);
            }
        }
        _pipe = null;
        _name = null;
    }
   
    void setPipe(InputPipe pipe) {
        _pipe = pipe;
    }
   
    private InputPipe _pipe = null;
    private String _name = null;
   
}
TOP

Related Classes of com.sun.enterprise.ee.web.sessmgmt.InputPipeWrapper$ReceivedMessageWrapper

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.