@Override protected void afterConnect() throws Exception { super.afterConnect(); setupNotificationConsumer(); }
private void internalCancelReferences() { cancelRefs(); if (queue != null) { queue.deliverAsync(); } }
protected void scheduleRetryConnectFixedTimeout(final long milliseconds) { try { cleanUpSessionFactory(csf); } catch (Throwable ignored) { } if (stopping) return; if (logger.isDebugEnabled()) { logger.debug("Scheduling retry for bridge " + this.name + " in " + milliseconds + " milliseconds"); } futureScheduledReconnection = scheduledExecutor.schedule(new FutureConnectRunnable(executor, this), milliseconds, TimeUnit.MILLISECONDS); }
if (stopping) return; csf = createSessionFactory(); if (csf == null) { scheduleRetryConnect(); return; scheduleRetryConnectFixedTimeout(100); return; scheduleRetryConnect(); return; afterConnect(); scheduleRetryConnectFixedTimeout(this.retryInterval); return; } else { ActiveMQServerLogger.LOGGER.errorConnectingBridgeRetry(this); scheduleRetryConnect(); fail(false); scheduleRetryConnect();
cleanUpSessionFactory(csf); } catch (Throwable dontCare) { fail(true); } catch (Exception e) { ActiveMQServerLogger.LOGGER.warn(e.getMessage(), e); fail(true); } else { logger.debug("Received invalid scaleDownTargetNodeID: " + scaleDownTargetNodeID); fail(me.getType() == ActiveMQExceptionType.DISCONNECTED); tryScheduleRetryReconnect(me.getType());
final Message message = beforeForward(ref.getMessage(), dest); if (message.isLargeMessage()) { deliveringLargeMessage = true; deliverLargeMessage(dest, ref, (LargeServerMessage) message); status = HandleStatus.HANDLED; } else { status = deliverStandardMessage(dest, ref, message);
protected Message beforeForward(final Message message, final SimpleString forwardingAddress) { if (useDuplicateDetection) { byte[] bytes = getDuplicateBytes(nodeUUID, message.getMessageID());
/** * @param ref * @param message * @return */ private HandleStatus deliverStandardMessage(SimpleString dest, final MessageReference ref, Message message) { // if we failover during send then there is a chance that the // that this will throw a disconnect, we need to remove the message // from the acks so it will get resent, duplicate detection will cope // with any messages resent if (logger.isTraceEnabled()) { logger.trace("going to send message: " + message + " from " + this.getQueue()); } try { producer.send(dest, message); } catch (final ActiveMQException e) { ActiveMQServerLogger.LOGGER.bridgeUnableToSendMessage(e, ref); synchronized (refs) { // We remove this reference as we are returning busy which means the reference will never leave the Queue. // because of this we have to remove the reference here refs.remove(message.getMessageID()); // The delivering count should also be decreased as to avoid inconsistencies ((QueueImpl) ref.getQueue()).decDelivering(ref); } connectionFailed(e, false); return HandleStatus.BUSY; } return HandleStatus.HANDLED; }
@Override public void connectionFailed(final ActiveMQException me, boolean failedOver) { connectionFailed(me, failedOver, null); }
@Override public void run() { bridge.connect(); } }
@Override protected Message beforeForward(final Message message, final SimpleString forwardingAddress) { // We make a copy of the message, then we strip out the unwanted routing id headers and leave // only // the one pertinent for the address node - this is important since different queues on different // nodes could have same queue ids // Note we must copy since same message may get routed to other nodes which require different headers Message messageCopy = message.copy(); if (logger.isTraceEnabled()) { logger.trace("Clustered bridge copied message " + message + " as " + messageCopy + " before delivery"); } // TODO - we can optimise this Set<SimpleString> propNames = new HashSet<>(messageCopy.getPropertyNames()); byte[] queueIds = message.getExtraBytesProperty(idsHeaderName); if (queueIds == null) { // Sanity check only ActiveMQServerLogger.LOGGER.noQueueIdDefined(message, messageCopy, idsHeaderName); throw new IllegalStateException("no queueIDs defined"); } for (SimpleString propName : propNames) { if (propName.startsWith(Message.HDR_ROUTE_TO_IDS)) { messageCopy.removeProperty(propName); } } messageCopy.putExtraBytesProperty(Message.HDR_ROUTE_TO_IDS, queueIds); messageCopy = super.beforeForward(messageCopy, forwardingAddress); return messageCopy; }
@Override public synchronized void start() throws Exception { if (started) { return; } started = true; stopping = false; activate(); if (notificationService != null) { TypedProperties props = new TypedProperties(); props.putSimpleStringProperty(new SimpleString("name"), name); Notification notification = new Notification(nodeUUID.toString(), CoreNotificationType.BRIDGE_STARTED, props); notificationService.sendNotification(notification); } }
Bridge bridge = new BridgeImpl(serverLocator, config.getInitialConnectAttempts(), config.getReconnectAttempts(), config.getReconnectAttemptsOnSameNode(), config.getRetryInterval(), config.getRetryIntervalMultiplier(), config.getMaxRetryInterval(), nodeManager.getUUID(), new SimpleString(config.getName()), queue, executorFactory.getExecutor(), FilterImpl.createFilter(config.getFilterString()), SimpleString.toSimpleString(config.getForwardingAddress()), scheduledExecutor, transformer, config.isUseDuplicateDetection(), config.getUser(), config.getPassword(), server, config.getRoutingType());
byte[] duplicateArray = BridgeImpl.getDuplicateBytes(server0.getNodeManager().getUUID(), id); duplicateTargetCache.addToCache(duplicateArray, tx);
@Override public void run() { try { producer.send(dest, message); // as soon as we are done sending the large message // we unset the delivery flag and we will call the deliveryAsync on the queue // so the bridge will be able to resume work unsetLargeMessageDelivery(); if (queue != null) { queue.deliverAsync(); } } catch (final ActiveMQException e) { unsetLargeMessageDelivery(); ActiveMQServerLogger.LOGGER.bridgeUnableToSendMessage(e, ref); connectionFailed(e, false); } } });
protected void fail(final boolean permanently) { logger.debug(this + "\n\t::fail being called, permanently=" + permanently); //we need to make sure we remove the node from the topology so any incoming quorum requests are voted correctly if (targetNodeID != null) { serverLocator.notifyNodeDown(System.currentTimeMillis(), targetNodeID); } if (queue != null) { try { if (logger.isTraceEnabled()) { logger.trace("Removing consumer on fail " + this + " from queue " + queue); } queue.removeConsumer(this); } catch (Exception dontcare) { logger.debug(dontcare); } } cancelRefs(); if (queue != null) { queue.deliverAsync(); } }