Package org.apache.synapse.message.store

Source Code of org.apache.synapse.message.store.RedeliveryProcessor$Worker

/*
*  Licensed to the Apache Software Foundation (ASF) under one
*  or more contributor license agreements.  See the NOTICE file
*  distributed with this work for additional information
*  regarding copyright ownership.  The ASF licenses this file
*  to you under the Apache License, Version 2.0 (the
*  "License"); you may not use this file except in compliance
*  with the License.  You may obtain a copy of the License at
*
*   http://www.apache.org/licenses/LICENSE-2.0
*
*  Unless required by applicable law or agreed to in writing,
*  software distributed under the License is distributed on an
*   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
*  KIND, either express or implied.  See the License for the
*  specific language governing permissions and limitations
*  under the License.
*/

package org.apache.synapse.message.store;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.synapse.FaultHandler;
import org.apache.synapse.MessageContext;
import org.apache.synapse.SynapseConstants;

/**
* Redelivery processor does the redelivery of the messages scheduled in the Message store
* It will poll the redelivery queue of the Message store and deliver messages according to
* a pre configured policy
*/
public class RedeliveryProcessor {

    private static final Log log = LogFactory.getLog(RedeliveryProcessor.class);

    /**hold reference to the associated message store */
    private MessageStore messageStore;

    /**Maximum number of redelivery's per message */
    private int maxRedeleveries = 1;

    /** Delay between two consecutive redelivery attempts */
    private int redeliveryDelay = 2000;

    /** enable/disable exponential backoff*/
    private boolean exponentialBackoff = false;

    /**the multipler that will be used in the exponential backoff algorithm */
    private int backOffMultiplier = -1;

    /** is Redelivery processr started*/
    private transient boolean start;


    public RedeliveryProcessor(MessageStore messageStore) {
        this.messageStore = messageStore;
    }

    /**
     * get the associated Message store
     * @return  message store
     */
    public MessageStore getMessageStore() {
        return messageStore;
    }

    /**
     * start the redelivery processor
     */
    public void start() {
        try {
            Thread.sleep(redeliveryDelay);
        } catch (InterruptedException e) {
            log.error(e);
        }

        Thread t = new Thread(new Worker());

        start = true;
        t.start();
        if (log.isDebugEnabled()) {
            log.debug("Redelivery Started");
        }
    }

    /**
     * stop the redelivery processor
     */
    public void stop() {
        start = false;
        if (log.isDebugEnabled()) {
            log.debug("Redelivery Stopped");
        }
    }

    /**
     * set the redelivery delay
     *
     * @param redeliveryDelay redelivery delay in milliseconds
     */
    public void setRedeliveryDelay(int redeliveryDelay) {
        this.redeliveryDelay = redeliveryDelay;
    }

    /**
     * set the Maximum number of redelivery's per message
     *
     * @param maxRedeleveries maximum number of redeliveries
     */
    public void setMaxRedeleveries(int maxRedeleveries) {
        this.maxRedeleveries = maxRedeleveries;
    }

    /**
     *
     * @return  is redelivery processor started
     */
    public boolean isStarted() {
        return start;
    }

    /**
     *
     * @return is exponental back off enable
     */
    public boolean isExponentialBackoffEnable() {
        return exponentialBackoff;
    }

    /**
     *
     * @param exponentialBackoff  true/false
     */
    public void setExponentialBackoff(boolean exponentialBackoff) {
        this.exponentialBackoff = exponentialBackoff;
    }

    /**
     *
     * @return the multipler that will be used in the exponential backoff algorithm
     */
    public int getBackOffMultiplier() {
        return backOffMultiplier;
    }

    /**
     * set Back of mutipller value to be used in the backoff algorithm
     *
     * @param backOffMultiplier factor for exponential backoff
     */
    public void setBackOffMultiplier(int backOffMultiplier) {
        this.backOffMultiplier = backOffMultiplier;
    }

    /**
     *
     * @return max number of redelivery's per message
     */
    public int getMaxRedeleveries() {
        return maxRedeleveries;
    }

    /**
     *
     * @return redelivery delay
     */
    public int getRedeliveryDelay() {
        return redeliveryDelay;
    }


    private class Worker implements Runnable {

        public void run() {
            while (start) {
                synchronized (messageStore) {

                    int delay = redeliveryDelay;
                    StorableMessage storableMessage;

                    storableMessage = messageStore.getFirstSheduledMessage();
                    if (storableMessage == null || storableMessage.getEndpoint() == null ||
                            !storableMessage.getEndpoint().readyToSend()) {
                        continue;
                    }

                    messageStore.dequeueScheduledQueue();
                    MessageContext synCtx = storableMessage.getMessageContext();

                    if (synCtx.getProperty(
                            SynapseConstants.MESSAGE_STORE_REDELIVERY_COUNT) == null) {
                        synCtx.setProperty(SynapseConstants.MESSAGE_STORE_REDELIVERY_COUNT, "1");
                        delay = redeliveryDelay;

                    } else {
                        String redeliveryCountStr = (String) synCtx.getProperty(
                                SynapseConstants.MESSAGE_STORE_REDELIVERY_COUNT);
                        int redeliveryCount = Integer.parseInt(redeliveryCountStr);

                        if (redeliveryCount >= maxRedeleveries) {
                            if (log.isDebugEnabled()) {
                                log.debug("Maximum number of redelivery attempts has exceeded " +
                                        "for the message: " + synCtx.getMessageID() + " - " +
                                        "Message will be put back to the message store.");
                            }
                            messageStore.store(storableMessage);
                            continue;
                        }

                        synCtx.setProperty(SynapseConstants.MESSAGE_STORE_REDELIVERY_COUNT, "" +
                                (redeliveryCount + 1));
                        if (maxRedeleveries <= (redeliveryCount + 1)) {
                            synCtx.setProperty(SynapseConstants.MESSAGE_STORE_REDELIVERED, "true");
                        }

                        if (exponentialBackoff && backOffMultiplier == -1) {
                            delay = (redeliveryCount + 1) * redeliveryDelay;
                        } else if (exponentialBackoff) {
                            delay = (int) Math.pow(backOffMultiplier, redeliveryCount) * redeliveryDelay;
                        }
                    }

                    try {
                        messageStore.wait(delay);
                    } catch (InterruptedException ignored) {

                    }

                    synCtx.pushFaultHandler((FaultHandler) storableMessage.getEndpoint());
                    storableMessage.getEndpoint().send(storableMessage.getMessageContext());

                    if (log.isDebugEnabled()) {
                        log.debug("Sent: " + storableMessage.getMessageContext().getEnvelope());
                    }
                }
            }
        }
    }
}
TOP

Related Classes of org.apache.synapse.message.store.RedeliveryProcessor$Worker

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.