Package org.openeai.jms.consumer.commands

Source Code of org.openeai.jms.consumer.commands.SyncCommandImpl

/*******************************************************************************
$Source: /cvs/repositories/openii3/project/java/source/org/openeai/jms/consumer/commands/SyncCommandImpl.java,v $
$Revision: 1.12 $
*******************************************************************************/

/**********************************************************************
This file is part of the OpenEAI Application Foundation or
OpenEAI Message Object API created by Tod Jackson
(tod@openeai.org) and Steve Wheat (steve@openeai.org) at
the University of Illinois Urbana-Champaign.

Copyright (C) 2002 The OpenEAI Software Foundation

This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2.1 of the License, or (at your option) any later version.

This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
Lesser General Public License for more details.

You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA

For specific licensing details and examples of how this software
can be used to build commercial integration software or to implement
integrations for your enterprise, visit http://www.OpenEai.org/licensing.
***********************************************************************/

package org.openeai.jms.consumer.commands;

import org.openeai.xml.*;
import org.openeai.config.*;

import org.openeai.moa.*;
import org.openeai.moa.jmsobjects.*;
import org.openeai.moa.objects.resources.*;

import org.openeai.jms.producer.PubSubProducer;
import org.openeai.jms.producer.MessageProducer;

import java.io.*;
import javax.jms.*;

import org.jdom.output.XMLOutputter;
import org.jdom.Document;
import org.jdom.Element;
import org.openeai.transport.ProducerId;


/**
* The "default" anscestor of all SyncCommands that are executed by a PubSubConsumer.
*<P>
* Organizations can add an additional layer between this class and the command implementations they develop
* or they can even eliminate the use of this class altogether.  This class provides many useful convenience
* methods that are commonly needed by all RequestCommand implementations.  Additional common routines will be added
* to this layer as time goes by...
* <P>
* @author      Tod Jackson (tod@openeai.org)
* @author      Steve Wheat (steve@openeai.org)
* @version     3.0  - 28 January 2003
*<P>
* @see ConsumerCommand
* @see RequestCommand
* @see RequestCommandImpl
* @see SyncCommand
*/
public class SyncCommandImpl extends ConsumerCommand {
  private Document m_syncErrorSyncDoc = null;
  private PubSubProducer m_syncErrorPublisher = null;
  private String m_syncErrorSyncPrimedDocumentUri = "";

  public SyncCommandImpl() {
  }

/**
  * Default constructor behavior that will apply to all SyncCommand implementations.
  * This is the constructor called by AppConfig/ConsumerConfig during gateway initialization.
  * Calls the ConsumerCommand constructor.  Additionally, this constructor verifies
  * that the SyncCommand implementation being initialized contains the appropriate
  * SyncErrorPublisher and SyncErrorSyncProperties objects in the CommandConfig
  * object passed in.
  *<P>
  * @param cConfig CommandConfig the CommandConfig Java object that wraps the CommandConfig
  * Element from the deployment document.
  * @throws InstantiationException if errors occur during initialization.
  */
  public SyncCommandImpl(CommandConfig cConfig) throws InstantiationException {
    super(cConfig);

    // must have a syncerrorsync primed document uri
    try {
      PropertyConfig pConfig = null;
      String uri = null;
      try {
        pConfig = (PropertyConfig)getAppConfig().getObject("SyncErrorSyncProperties");
      }
      catch (Exception e) {
        // temporarily ignoring this error and letting it fall through...
      }
      if (pConfig == null) {
        logger.warn("Missing 'SyncErrorSyncProperties' PropertyConfig element in configuration document.");
      }
      else {
        uri = pConfig.getProperties().getProperty("SyncErrorSyncPrimedDocumentUri",null);
      }
      if (uri == null) {
        logger.warn("Missing 'SyncErrorSyncPrimedDocumentUri' property in 'SyncErrorSyncProperties' PropertyConfig element.  Can't continue.");
      }
      setSyncErrorSyncPrimedDocumentUri(uri);
    }
    catch (Exception e) {
      logger.fatal("Exception occurred obtaining 'SyncErrorSyncPrimedDocumentUri' property.  Can't continue.");
      logger.fatal(e.getMessage(), e);
      throw new InstantiationException(e.getMessage());
    }

    // must have a sync error publisher...
    try {
      setSyncErrorPublisher((PubSubProducer)getAppConfig().getObject("SyncErrorPublisher"));
    }
    catch (Exception e) {
      String errorMessage = "[SyncCommand] Could not find SyncErrorPublisher in AppConfig!  Exception: " + e.getMessage();
      logger.fatal(errorMessage);
      throw new InstantiationException(errorMessage);
    }
    if (getSyncErrorPublisher().isStarted() == false) {
      try {
        if (getSyncErrorPublisher().startPublisher() == false) {
          String errorMessage = "[SyncCommand] Could not start SyncErrorPublisher!";
          logger.fatal(errorMessage);
          throw new InstantiationException(errorMessage);
        }
      }
      catch (JMSException e) {
        String errorMessage = "[SyncCommand] Exception starting SyncErrorPublisher!  Exception: " + e.getMessage();
        logger.fatal(errorMessage);
        throw new InstantiationException(errorMessage);
      }
    }
  }

  /**
  * Returns the Sync-Error-Sync primed document URI that will be used to build
  * the primed sync error sync Document used as a starting point when publishing
  * Sync errors.
  * <P>
  * @return String the URI.
  **/
  final protected String getSyncErrorSyncPrimedDocumentUri() {
    return m_syncErrorSyncPrimedDocumentUri;
  }
  /**
  * Sets the Sync-Error-Sync primed document URI that will be used to build
  * the primed sync error sync Document used as a starting point when publishing
  * Sync errors.
  * <P>
  * @param uri String the URI.
  **/
  final protected void setSyncErrorSyncPrimedDocumentUri(String uri) {
    m_syncErrorSyncPrimedDocumentUri = uri;
  }

  /**
  * Sets the Sync-Error-Sync primed Document object built from the
  * SyncErrorSyncPrimedDocument URI that will be used as
  * the primed sync error sync Document used as a starting point
  * when publishing Sync errors.
  * <P>
  * @param doc Document the primed sync error document
  **/
  public final void setSyncErrorSyncDoc(Document doc) {
    m_syncErrorSyncDoc = doc;
  }
  /**
  * Returns the Sync-Error-Sync primed Document object built from the
  * SyncErrorSyncPrimedDocument URI that will be used as
  * the primed sync error sync Document used as a starting point
  * when publishing Sync errors.
  * <P>
  * @return Document the primed sync error document
  **/
  public final Document getSyncErrorSyncDoc() {
    return m_syncErrorSyncDoc;
  }

/**
  *  Set SyncErrorPublisher associated to this command.  This is only required if the command
  *  is an implementation of SyncCommand.  It is called in the
  *  constructor of Command.
  *  @param pubSub PubSubProducer
  */
  private void setSyncErrorPublisher(PubSubProducer pubSub) {
    m_syncErrorPublisher = pubSub;
  }
/**
  *  Get SyncErrorPublisher associated to this command.  It is called by commands
  *  when they need to publish a sync error via the publishSyncError method also
  *  defined in Command.
  *  @return  PubSubProducer
  */
  public final PubSubProducer getSyncErrorPublisher() {
    return m_syncErrorPublisher;
  }

/**
  *  This method is used to publish a Sync-Error-Sync message when/if the Command has
  *  any errors during processing (during the 'execute' method).
  *<P>
  @param senderControlArea Element the control area from the message consumed by the Command.  This will be used
  *  to determine the message action and Requesting message id information (the messaging component that
  *  published the message this Command consumed).
  *<P>
  @param errors java.util.List a List of org.openeai.moa.objects.Error objects that have
  *  been built with the appropriate error number, error type and error descriptions.
  *<P>
  @param e Throwable an exception that has occurred in the ScheduledCommand.  This exception will be added
  *  to the list of errors passed in.
  */
  final protected void publishSyncError(Element senderControlArea, java.util.List errors, Throwable e) {
    org.openeai.moa.objects.resources.Error anError =
      new org.openeai.moa.objects.resources.Error();

    ByteArrayOutputStream bw = new ByteArrayOutputStream();
    PrintWriter pw = new PrintWriter(bw, true);
    e.printStackTrace(pw);
    String errMessage = "Exception: " + e.getMessage() + "\n" + bw.toString();

    anError.setType("system");
    anError.setErrorNumber("COMMAND-1001");
    anError.setErrorDescription(errMessage);

    errors.add(anError);
    publishSyncError(senderControlArea, errors);
  }

/**
  *  This method is used to publish a Sync-Error-Sync message when/if the Command has
  *  any errors during processing (during the 'execute' method).
  *<P>
  @param senderControlArea Element the control area from the message consumed by the Command.  This will be used
  *  to determine the message action and Requesting message id information (the messaging component that
  *  published the message this Command consumed).
  *<P>
  @param errors java.util.List a List of org.openeai.moa.objects.Error objects that have
  *  been built with the appropriate error number, error type and error descriptions.
  */
  final protected void publishSyncError(Element senderControlArea, java.util.List errors) {

    XmlDocumentReader xmlReader = new XmlDocumentReader();
    Document syncErrorDoc = null;
    try {
      syncErrorDoc =
        xmlReader.initializeDocument(getSyncErrorSyncPrimedDocumentUri(), getOutboundXmlValidation());
      if (syncErrorDoc == null) {
        String errMessage = "[PublishSyncError] Missing 'SyncErrorSyncPrimedDocumentUri' property in configuration document.  Can't publish sync error.";
        logger.fatal(errMessage);
        return;
      }
    }
    catch (XmlDocumentReaderException e) {
      logger.fatal("[PublishSyncError] Error initializing Sync-Error-Sync primed document, could not publish the sync error sync message.");
      logger.fatal(e.getMessage(), e);
      return;
    }

    Element eControlArea = getControlArea(syncErrorDoc.getRootElement());

    Result aResult = new Result();

    ProcessedMessageId processedMsgId = new ProcessedMessageId();

    String action = null;
    if (senderControlArea.getContentSize()==0) {
      // an empty control area was passed so we can't use it.
      // We'll have to use the primed document's control area.
      processedMsgId.setProducerId("None");
      processedMsgId.setSenderAppId("None");
      processedMsgId.setMessageSeq("None");
    }
    else {
      // Build the dynamic portion of the sync document's control area
      // This is going to have the sending application's "Sender" information in it
      // that we'll need to use to build the Result object in our
      // sync error document.
      // Our sender information will go in the "Sender" element of the primed
      // document
      // Set the sender element

      // Build the ProcessedMessageId Object out of the contents of the
      // Sender's control area.
      try {
        action = senderControlArea.getAttribute(MESSAGE_ACTION).getValue();
        Element eSender = senderControlArea.getChild("Sender");

        processedMsgId.setProducerId(eSender.getChild("MessageId").
          getChild("ProducerId").getText());
        processedMsgId.setSenderAppId(eSender.getChild("MessageId").
          getChild("SenderAppId").getText());
        processedMsgId.setMessageSeq(eSender.getChild("MessageId").
          getChild("MessageSeq").getText());
      }
      catch (Exception e) {
        logger.fatal("Error building ProcessedMessageId Element in Sync-Error-Sync message!");
        logger.fatal(e.getMessage(), e);
      }
    }

    // This is the control area information relevant to this Gateway
    eControlArea.removeChild("Result");
    eControlArea.removeChild("Datetime");
    eControlArea.removeChild("Sender");

    Sender sender = new Sender();
    MessageId msgId = new MessageId();
    msgId.setProducerId(getSyncErrorPublisher().getProducerId(null).getId());
    msgId.setSenderAppId(getAppName());
    msgId.setMessageSeq(Integer.toString(getSyncErrorPublisher().incrementMessageSequence()));

    sender.setMessageId(msgId);

    Authentication auth = new Authentication();
    auth.setAuthUserId(getAppName());
    auth.setAuthUserSignature(getAppName());
    sender.setAuthentication(auth);

    Element eSender = null;
    try {
      eSender = (Element)sender.buildOutputFromObject();
    }
    catch (Exception e) {
      logger.fatal("[publishSyncError1] Exception occurred building an Element from the Sender object.  Can't publish Sync error.  Exception: " + e.getMessage());
      logger.fatal(e.getMessage(), e);
      return;
    }

    // Set the datetime element
    Datetime dt = new Datetime();
    Element eDatetime = null;
    try {
      eDatetime = (Element)dt.buildOutputFromObject();
    }
    catch (Exception e) {
      logger.fatal("[publishSyncError1] Exception occurred building an Element from the Datetime object.  Can't publish Sync error.  Exception: " + e.getMessage());
      logger.fatal(e.getMessage(), e);
      return;
    }

    eControlArea.addContent(eSender);
    eControlArea.addContent(eDatetime);

    if (action == null) {
      action = "Unknown";
    }
    aResult.setAction(action);
    aResult.setStatus("failure");
    aResult.setProcessedMessageId(processedMsgId);

    for (int i=0; i<errors.size(); i++) {
      org.openeai.moa.objects.resources.Error anError =
        (org.openeai.moa.objects.resources.Error)errors.get(i);
      aResult.addError(anError);
    }

    try {
      Element eResult = (Element)aResult.buildOutputFromObject();
      eControlArea.addContent(eResult);
      syncErrorDoc.getRootElement().removeContent(eControlArea);
      syncErrorDoc.getRootElement().addContent(eControlArea);
      TextMessage syncErrorMessage = getSyncErrorPublisher().createTextMessage();
      XMLOutputter xmlOut = new XMLOutputter();
      syncErrorMessage.setText(xmlOut.outputString(syncErrorDoc));
      if (getSyncErrorPublisher().getDefaultCommandName().length() == 0 ||
        getSyncErrorPublisher().getDefaultCommandName() == null) {
        getSyncErrorPublisher().setDefaultCommandName("EnterpriseSyncErrorSync");
      }
      syncErrorMessage.setStringProperty(MessageProducer.MESSAGE_ID,msgId.toString());
      syncErrorMessage.setStringProperty(MessageProducer.COMMAND_NAME,getSyncErrorPublisher().getDefaultCommandName());
        //TODO: change this...
      getSyncErrorPublisher().publishMessage(syncErrorMessage);
    }
    catch (Exception e) {
      logger.fatal("Error publishing Sync-Error-Sync message!");
      logger.fatal(e.getMessage(), e);
    }
  }
}
TOP

Related Classes of org.openeai.jms.consumer.commands.SyncCommandImpl

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.