use of com.sun.messaging.jmq.jmsserver.util.BrokerException in project openmq by eclipse-ee4j.
the class RollbackCommitHandler method handle.
/**
* Handle the incomming administration message.
*
* @param con The Connection the message came in on.
* @param cmd_msg The administration message
* @param cmd_props The properties from the administration message
*/
@Override
public boolean handle(IMQConnection con, Packet cmd_msg, Hashtable cmd_props) {
if (DEBUG) {
logger.log(Logger.DEBUG, this.getClass().getName() + ": " + "Rollback/Commit transaction " + cmd_props);
}
// Get the admin request message type
int requestType = ((Integer) cmd_props.get(MessageType.JMQ_MESSAGE_TYPE)).intValue();
int status = Status.OK;
String errMsg = null;
TransactionUID tid = null;
TransactionState ts = null;
TransactionHandler thandler = null;
// Get the packet handler that handles transaction packets
if (parent.adminPktRtr != null) {
thandler = (TransactionHandler) parent.adminPktRtr.getHandler(PacketType.ROLLBACK_TRANSACTION);
}
Long id = (Long) cmd_props.get(MessageType.JMQ_TRANSACTION_ID);
// only applies to rollback request
Boolean v = (Boolean) cmd_props.get(MessageType.JMQ_PROCESS_ACTIVE_CONSUMERS);
boolean processActiveConsumers = (v != null && v.booleanValue());
HAMonitorService hamonitor = Globals.getHAMonitorService();
if (hamonitor != null && hamonitor.inTakeover()) {
status = Status.ERROR;
errMsg = rb.getString(rb.E_CANNOT_PROCEED_TAKEOVER_IN_PROCESS);
logger.log(Logger.ERROR, this.getClass().getName() + ": " + errMsg);
}
if (id != null) {
tid = new TransactionUID(id.longValue());
} else {
status = Status.BAD_REQUEST;
}
if (status == Status.OK) {
TransactionList[] tls = DL.getTransactionList(null);
TransactionList tl = null;
for (int i = 0; i < tls.length; i++) {
tl = tls[i];
ts = tl.retrieveState(tid);
if (ts == null) {
continue;
}
break;
}
if (ts == null) {
// Specified transaction did not exist
status = Status.NOT_FOUND;
errMsg = rb.getString(rb.E_NO_SUCH_TRANSACTION, tid);
} else if (requestType == MessageType.COMMIT_TRANSACTION && ts.getState() != TransactionState.PREPARED) {
status = Status.PRECONDITION_FAILED;
errMsg = rb.getString(rb.E_TRANSACTION_NOT_PREPARED, tid);
} else if (requestType == MessageType.ROLLBACK_TRANSACTION && (ts.getState() < TransactionState.STARTED || ts.getState() > TransactionState.PREPARED)) {
status = Status.PRECONDITION_FAILED;
errMsg = rb.getString(rb.E_INVALID_TXN_STATE_FOR_ROLLBACK, tid);
} else {
JMQXid xid = tl.UIDToXid(tid);
if (xid == null && (!(Globals.getHAEnabled() && ts.getState() == TransactionState.PREPARED))) {
/*
* Need to pick the right error message: If (action is ROLLBACK and state is one of {STARTED, FAILED, INCOMPLETE,
* COMPLETE}) "Rollback of non-XA transaction 123456789 in non-PREPARED state is not supported." else
* "Could not find Xid for 123456789"
*/
if (requestType == MessageType.ROLLBACK_TRANSACTION && (ts.getState() >= TransactionState.STARTED && ts.getState() < TransactionState.PREPARED)) {
errMsg = rb.getString(rb.E_INTERNAL_BROKER_ERROR, "Rollback of non-XA transaction " + tid + " in non-PREPARED state is not supported.");
} else {
errMsg = rb.getString(rb.E_INTERNAL_BROKER_ERROR, "Could not find Xid for " + tid);
}
status = Status.ERROR;
} else if (thandler == null) {
errMsg = rb.getString(rb.E_INTERNAL_BROKER_ERROR, "Could not locate TransactionHandler");
status = Status.ERROR;
} else {
if (requestType == MessageType.ROLLBACK_TRANSACTION) {
if (DEBUG) {
logger.log(Logger.DEBUG, "Rolling back " + tid + " in state " + ts);
}
try {
if (processActiveConsumers) {
logger.log(logger.INFO, rb.getKString(rb.I_ADMIN_REDELIVER_MSGS_ON_TXN_ROLLBACK, tid));
try {
thandler.redeliverUnacked(tl, tid, true, true, true, -1, false);
} catch (Exception e) {
logger.logStack(logger.WARNING, rb.getKString(rb.X_ADMIN_REDELIVER_MSG_ON_TXN_ROLLBACK, tid, e.getMessage()), e);
}
}
thandler.doRollback(tl, tid, xid, null, ts, null, con, RollbackReason.ADMIN);
} catch (BrokerException e) {
status = Status.ERROR;
errMsg = e.getMessage();
}
} else if (requestType == MessageType.COMMIT_TRANSACTION) {
if (DEBUG) {
logger.log(Logger.DEBUG, "Committing " + tid + " in state " + ts);
}
try {
thandler.doCommit(tl, tid, xid, Integer.valueOf(XAResource.TMNOFLAGS), ts, null, false, con, null);
} catch (BrokerException e) {
status = Status.ERROR;
errMsg = e.getMessage();
}
} else {
// Should never happen.
return super.handle(con, cmd_msg, cmd_props);
}
}
}
}
sendReply(con, cmd_msg, requestType + 1, status, errMsg);
return true;
}
use of com.sun.messaging.jmq.jmsserver.util.BrokerException in project openmq by eclipse-ee4j.
the class MigrateStoreHandler method handle.
/**
* Handle the incomming administration message.
*
* @param con The Connection the message came in on.
* @param cmd_msg The administration message
* @param cmd_props The properties from the administration message
*/
@Override
public boolean handle(IMQConnection con, Packet cmd_msg, Hashtable cmd_props) {
boolean noop = true;
int status = Status.OK;
String errMsg = "";
if (DEBUG) {
logger.log(Logger.INFO, this.getClass().getName() + ": " + "Request migrate this broker''s store: " + cmd_props);
}
String brokerID = (String) cmd_props.get(MessageType.JMQ_BROKER_ID);
String partition = (String) cmd_props.get(MessageType.JMQ_MIGRATESTORE_PARTITION);
if (partition == null) {
if (brokerID != null) {
logger.log(Logger.INFO, BrokerResources.I_ADMIN_MIGRATESTORE_TO, brokerID);
} else {
logger.log(Logger.INFO, BrokerResources.I_ADMIN_MIGRATESTORE);
}
} else {
logger.log(Logger.INFO, "XXXAdmin request migrate this broker's store partition " + partition + " to broker " + brokerID);
}
HAMonitorService hamonitor = Globals.getHAMonitorService();
if (hamonitor != null && hamonitor.inTakeover()) {
status = Status.NOT_MODIFIED;
errMsg = rb.getString(rb.E_CANNOT_PROCEED_TAKEOVER_IN_PROCESS);
logger.log(Logger.ERROR, this.getClass().getName() + ": " + errMsg);
}
if (status == Status.OK) {
if (partition == null && Globals.getHAEnabled()) {
status = Status.NOT_MODIFIED;
errMsg = rb.getKString(rb.E_OPERATION_NOT_SUPPORTED_IN_HA, MessageType.getString(MessageType.MIGRATESTORE_BROKER));
logger.log(Logger.ERROR, errMsg);
}
}
if (status == Status.OK) {
if (Globals.isJMSRAManagedBroker()) {
status = Status.NOT_MODIFIED;
errMsg = "Can not process migration store request because this broker's life cycle is JMSRA managed";
logger.log(Logger.ERROR, this.getClass().getName() + ": " + errMsg);
}
}
UID partitionID = null;
if (status == Status.OK) {
if (partition != null) {
try {
long v = Long.parseLong(partition);
partitionID = new UID(v);
} catch (Exception e) {
partitionID = null;
status = Status.NOT_MODIFIED;
errMsg = "XXXCan not process migration partition " + partition + " request because unable to parse " + partition + ": " + e;
logger.log(Logger.ERROR, errMsg);
}
}
}
if (status == Status.OK) {
if (partitionID != null && brokerID == null) {
status = Status.NOT_MODIFIED;
errMsg = "XXXCan not process migration partition " + partitionID + " request because brokerID not specified";
logger.log(Logger.ERROR, errMsg);
}
}
if (status == Status.OK) {
if (partitionID != null && !(DL.isPartitionMode() && DL.isPartitionMigratable())) {
status = Status.NOT_MODIFIED;
errMsg = "XXXCan not process migration partition " + partitionID + " request because partition mode not enabled";
logger.log(Logger.ERROR, errMsg);
}
}
if (status == Status.OK) {
if (partitionID != null) {
DestinationList dl = DL.getDestinationList(partitionID);
if (dl == null) {
status = Status.NOT_MODIFIED;
errMsg = "XXXCan not process migration partition " + partitionID + " request because partition " + partitionID + " not found";
logger.log(Logger.ERROR, errMsg);
} else if (dl.getPartitionedStore().isPrimaryPartition()) {
status = Status.NOT_MODIFIED;
errMsg = "XXXCan not process migration partition " + partitionID + " request because partition " + partitionID + " is the primary partition";
logger.log(Logger.ERROR, errMsg);
}
}
}
if (status == Status.OK) {
if (brokerID == null) {
try {
brokerID = getBrokerID();
} catch (Throwable t) {
status = Status.NOT_MODIFIED;
errMsg = "Unable to get a connected broker to takeover this broker's store: " + t.getMessage();
if ((t instanceof OperationNotAllowedException) && ((OperationNotAllowedException) t).getOperation().equals(MessageType.getString(MessageType.MIGRATESTORE_BROKER))) {
logger.log(logger.ERROR, errMsg);
} else {
logger.logStack(logger.ERROR, errMsg, t);
}
}
}
}
if (status != Status.OK) {
sendReply(con, cmd_msg, brokerID, null, errMsg, status, null);
return true;
}
try {
BrokerStateHandler.setExclusiveRequestLock(ExclusiveRequest.MIGRATE_STORE);
} catch (Throwable t) {
status = Status.PRECONDITION_FAILED;
if (t instanceof BrokerException) {
status = ((BrokerException) t).getStatusCode();
}
errMsg = MessageType.getString(MessageType.MIGRATESTORE_BROKER) + ": " + Status.getString(status) + " - " + t.getMessage();
logger.log(Logger.ERROR, errMsg);
status = Status.NOT_MODIFIED;
}
try {
if (partitionID != null) {
migratePartition(con, cmd_msg, partitionID, brokerID);
return true;
}
Long syncTimeout = null;
final BrokerStateHandler bsh = Globals.getBrokerStateHandler();
if (status == Status.OK) {
try {
syncTimeout = (Long) cmd_props.get(MessageType.JMQ_MIGRATESTORE_SYNC_TIMEOUT);
ClusterManager cm = Globals.getClusterManager();
BrokerMQAddress self = (BrokerMQAddress) cm.getMQAddress();
BrokerMQAddress master = (cm.getMasterBroker() == null ? null : (BrokerMQAddress) cm.getMasterBroker().getBrokerURL());
if (self.equals(master)) {
throw new BrokerException(rb.getKString(rb.E_CHANGE_MASTER_BROKER_FIRST, MessageType.getString(MessageType.MIGRATESTORE_BROKER)), Status.NOT_ALLOWED);
}
} catch (Throwable t) {
status = Status.PRECONDITION_FAILED;
if (t instanceof BrokerException) {
status = ((BrokerException) t).getStatusCode();
}
errMsg = MessageType.getString(MessageType.MIGRATESTORE_BROKER) + ": " + Status.getString(status) + " - " + t.getMessage();
logger.log(Logger.ERROR, errMsg);
status = Status.NOT_MODIFIED;
}
}
SysMessageID replyMessageID = null;
String replyStatusStr = null;
try {
// shutdown if !noop
String hostport = null;
if (status == Status.OK) {
try {
noop = false;
hostport = bsh.takeoverME(brokerID, syncTimeout, con);
} catch (BrokerException ex) {
status = ex.getStatusCode();
if (status == Status.BAD_REQUEST || status == Status.NOT_ALLOWED || status == Status.NOT_MODIFIED || status == Status.UNAVAILABLE || status == Status.PRECONDITION_FAILED) {
status = Status.PRECONDITION_FAILED;
if (ex instanceof OperationNotAllowedException) {
if (((OperationNotAllowedException) ex).getOperation().equals(MessageType.getString(MessageType.MIGRATESTORE_BROKER))) {
status = Status.NOT_MODIFIED;
noop = true;
}
}
errMsg = Globals.getBrokerResources().getKString(BrokerResources.E_FAIL_MIGRATESTORE_NOT_MIGRATED, ex.getMessage());
if (noop) {
logger.log(Logger.ERROR, errMsg);
} else {
logger.logStack(Logger.ERROR, errMsg, ex);
}
} else {
status = Status.EXPECTATION_FAILED;
errMsg = Globals.getBrokerResources().getKString(BrokerResources.E_FAIL_TAKEOVERME, brokerID, ex.getMessage());
logger.logStack(Logger.ERROR, errMsg, ex);
}
}
}
if (status == Status.OK) {
try {
Globals.getClusterBroadcast().stopClusterIO(false, true, null);
} catch (Throwable t) {
logger.logStack(Logger.WARNING, "Failed to stop cluster IO", t);
}
}
List ret = sendReply(con, cmd_msg, brokerID, hostport, errMsg, status, null);
replyMessageID = (SysMessageID) ret.get(0);
replyStatusStr = (String) ret.get(1);
} finally {
final SysMessageID mid = replyMessageID;
final String statusStr = replyStatusStr;
if (!noop) {
try {
if (con instanceof IMQBasicConnection) {
IMQBasicConnection ipCon = (IMQBasicConnection) con;
ipCon.flushControl(1000);
}
try {
Globals.getServiceManager().stopNewConnections(ServiceType.NORMAL);
} catch (Exception e) {
logger.logStack(logger.WARNING, rb.getKString(rb.W_STOP_SERVICE_FAIL, ServiceType.getServiceTypeString(ServiceType.NORMAL), e.getMessage()), e);
}
try {
Globals.getServiceManager().stopNewConnections(ServiceType.ADMIN);
} catch (Exception e) {
logger.logStack(logger.WARNING, rb.getKString(rb.W_STOP_SERVICE_FAIL, ServiceType.getServiceTypeString(ServiceType.ADMIN), e.getMessage()), e);
}
BrokerStateHandler.setShuttingDown(true);
bsh.prepareShutdown(false, true);
waitForHandlersToComplete(20);
if (mid == null) {
logger.log(Logger.INFO, BrokerResources.I_ADMIN_SHUTDOWN_REQUEST);
bsh.initiateShutdown("admin", 0, false, 0, true);
return true;
}
final String waitstr = rb.getKString(rb.I_WAIT_ADMIN_RECEIVE_REPLY, MessageType.getString(MessageType.MIGRATESTORE_BROKER_REPLY) + "[" + statusStr + "]");
final long totalwait = Globals.getConfig().getIntProperty(MAX_WAIT_ADMIN_CLIENT_PROP, DEFAULT_MAX_WAIT_ADMIN_CLIENT) * 1000L;
final IMQConnection conn = con;
Executors.newSingleThreadExecutor().execute(new Runnable() {
@Override
public void run() {
try {
long waited = 0L;
while (conn.getConnectionState() < Connection.STATE_CLEANED && waited < totalwait) {
logger.log(logger.INFO, waitstr);
try {
Thread.sleep(500);
waited += 500L;
} catch (Exception e) {
/* ignore */
}
}
logger.log(Logger.INFO, BrokerResources.I_ADMIN_SHUTDOWN_REQUEST);
bsh.initiateShutdown("admin-migratestore-shutdown", 0, false, 0, true);
} catch (Throwable t) {
bsh.initiateShutdown("admin-migratestore-shutdown::[" + t.toString() + "]", 0, false, 0, true);
}
}
});
} catch (Throwable t) {
bsh.initiateShutdown("admin-migratestore-shutdown:[" + t.toString() + "]", 0, false, 0, true);
}
}
}
} finally {
BrokerStateHandler.unsetExclusiveRequestLock(ExclusiveRequest.MIGRATE_STORE);
}
return true;
}
use of com.sun.messaging.jmq.jmsserver.util.BrokerException in project openmq by eclipse-ee4j.
the class ProtocolImpl method startTransaction.
/**
* Start a transaction.
*
* @param xid The Xid of the transaction to start. Required if transaction is an XA transaction. Must be null if it is
* not an XA transaction.
* @param xaFlags xaFlags passed on START operation. Used only if an XA transaction.
* @param con Connection client start packet came in on (or null if internal)
* @param type how rollback should be handled (e.g. only not prepared)
* @param lifetime how long the transaction should live (0 == forever)
* @return The TransactionUID started
*/
@Override
public TransactionUID startTransaction(JMQXid xid, Integer xaFlags, AutoRollbackType type, long lifetime, IMQConnection con) throws BrokerException {
if (DEBUG) {
logger.log(Logger.INFO, "ProtocolImpl.START TRANSACTION:XID=" + xid + ", xaFlags=" + TransactionState.xaFlagToString(xaFlags) + ", type=" + type + ", lifetime=" + lifetime + ", conn=@" + con.hashCode() + "[" + con.getConnectionUID() + ", " + con + "]");
}
List conlist = con.getTransactionListThreadSafe();
TransactionHandler handler = (TransactionHandler) pr.getHandler(PacketType.START_TRANSACTION);
// allocated a TID
TransactionUID id = null;
TransactionList tl = null;
if (xaFlags == null || TransactionState.isFlagSet(XAResource.TMNOFLAGS, xaFlags)) {
id = new TransactionUID();
TransactionList[] tls = DL.getTransactionList(con.getPartitionedStore());
tl = tls[0];
if (tl == null) {
throw new BrokerException("No transaction List for connection " + con + " to start new transaction " + id + (xid == null ? "" : " XID=" + xid));
}
} else if (xid != null) {
Object[] oo = TransactionList.mapXidToTid(xid, con);
if (oo == null) {
throw new BrokerException("Unknown XID " + xid, Status.NOT_FOUND);
} else {
tl = (TransactionList) oo[0];
id = (TransactionUID) oo[1];
}
} else {
// XID is null, something is wrong
throw new BrokerException("Invalid xid");
}
if (tl == null) {
Object[] oo = TransactionList.getTransListAndState(id, con, false, false);
if (oo != null) {
tl = (TransactionList) oo[0];
}
}
if (tl == null) {
throw new BrokerException("No Transaction List found for connection " + con + " to start transaction " + id + (xid == null ? "" : " XID=" + xid));
}
Object o = new Object();
handler.doStart(tl, id, conlist, con, type, xid, xid != null, lifetime, 0, xaFlags, PacketType.START_TRANSACTION, false, o.toString());
if (DEBUG) {
logger.log(Logger.INFO, "ProtocolImpl.STARTED TRANSACTION:TID=" + id + ", XID=" + xid + ", type=" + type + ", con=" + con);
}
return id;
}
use of com.sun.messaging.jmq.jmsserver.util.BrokerException in project openmq by eclipse-ee4j.
the class ProtocolImpl method commitTransaction.
/**
* Commit a transaction.
*
* @param id The TransactionUID to commit
* @param xid The Xid of the transaction to commit. Required if transaction is an XA transaction. Must be null if it is
* not an XA transaction.
* @param xaFlags xaFlags passed on COMMIT operation. Used only if an XA transaction.
* @param con Connection client commit packet came in on (or null if internal)
*/
@Override
public void commitTransaction(TransactionUID id, JMQXid xid, Integer xaFlags, IMQConnection con) throws BrokerException {
if (DEBUG) {
logger.log(Logger.INFO, "ProtocolImpl.COMMIT TRANSACTION:TID=" + id + ", XID=" + xid + ", xaFlags=" + TransactionState.xaFlagToString(xaFlags) + ", conn=@" + con.hashCode() + "[" + con.getConnectionUID() + ", " + con + "]");
}
List conlist = con.getTransactionListThreadSafe();
TransactionHandler handler = (TransactionHandler) pr.getHandler(PacketType.START_TRANSACTION);
TransactionList tl = null;
if (0L == id.longValue()) {
if (xid == null) {
throw new BrokerException("Unexpected TransactionUID " + id);
}
Object[] oo = TransactionList.mapXidToTid(xid, con);
if (oo == null) {
id = null;
} else {
tl = (TransactionList) oo[0];
id = (TransactionUID) oo[1];
}
if (id == null) {
throw new BrokerException("Unknown XID " + xid, Status.NOT_FOUND);
}
}
TransactionState ts = null;
if (tl == null) {
Object[] oo = TransactionList.getTransListAndState(id, con, false, false);
if (oo != null) {
tl = (TransactionList) oo[0];
ts = (TransactionState) oo[1];
}
}
if (tl == null) {
throw new BrokerException("Unknown transaction " + id + (xid == null ? "" : " XID=" + xid), Status.NOT_FOUND);
}
if (ts == null) {
ts = tl.retrieveState(id);
if (ts == null) {
throw new BrokerException("Unknown transaction " + id + (xid == null ? "" : " XID=" + xid), Status.NOT_FOUND);
}
}
if (xid != null) {
if (ts.getXid() == null || !xid.equals(ts.getXid())) {
throw new BrokerException("Transaction XID mismatch " + xid + ", expected " + ts.getXid() + " for transaction " + id);
}
}
handler.doCommit(tl, id, xid, xaFlags, ts, conlist, false, con, null);
}
use of com.sun.messaging.jmq.jmsserver.util.BrokerException in project openmq by eclipse-ee4j.
the class ProtocolImpl method pauseSession.
/**
* Pause a session
* <P>
* Packet:<B>STOP</b>
* </p>
*
* @param uid session to pause
*/
@Override
public void pauseSession(SessionUID uid) throws BrokerException {
Session ses = Session.getSession(uid);
if (ses == null) {
throw new BrokerException("No session for " + uid);
}
ses.pause("PROTOCOL");
}
Aggregations