/*
 * 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.myfaces.extensions.cdi.jsf.impl.scope.conversation;

import org.apache.myfaces.extensions.cdi.core.impl.scope.conversation.spi.BeanEntry;
import org.apache.myfaces.extensions.cdi.core.api.scope.conversation.config.ConversationConfig;
import org.apache.myfaces.extensions.cdi.core.api.scope.conversation.event.CloseConversationEvent;
import org.apache.myfaces.extensions.cdi.core.api.scope.conversation.event.RestartConversationEvent;
import org.apache.myfaces.extensions.cdi.jsf.impl.scope.conversation.spi.ConversationKey;
import org.apache.myfaces.extensions.cdi.jsf.impl.scope.conversation.spi.EditableConversation;
import org.apache.myfaces.extensions.cdi.jsf.impl.util.RequestCache;

import javax.enterprise.inject.Typed;
import javax.enterprise.inject.spi.BeanManager;
import java.io.Serializable;
import java.util.Set;

/**
 * {@inheritDoc}
 */
@Typed()
public class DefaultConversation implements EditableConversation
{
    private static final long serialVersionUID = -2958548175169003298L;

    @SuppressWarnings({"FieldCanBeLocal", "UnusedDeclaration"})
    private final ConversationKey conversationKey;
    private ConversationExpirationEvaluator expirationEvaluator;

    //all implementations will be serializable
    private BeanManager beanManager;

    private final BeanStorage beanStorage;

    private final boolean closeConversationEventEnable;
    private final boolean restartConversationEventEnable;

    /**
     * Constructor which creates a conversation for the given
     * {@link ConversationKey}, {@link ConversationExpirationEvaluator}, {@link ConversationConfig}
     * and {@link BeanManager}
     * @param conversationKey key of the current conversation
     * @param expirationEvaluator expiration strategy which decides if the current conversation is expired
     * @param conversationConfig current conversation-config
     * @param beanManager current bean-manager
     */
    public DefaultConversation(ConversationKey conversationKey,
                               ConversationExpirationEvaluator expirationEvaluator,
                               ConversationConfig conversationConfig,
                               BeanManager beanManager)
    {
        this.conversationKey = conversationKey;
        this.expirationEvaluator = expirationEvaluator;
        this.beanManager = beanManager;
        this.beanStorage = new BeanStorage(this.beanManager);

        this.closeConversationEventEnable = conversationConfig.isCloseConversationEventEnabled();
        this.restartConversationEventEnable = conversationConfig.isRestartConversationEventEnabled();

        if(this.expirationEvaluator instanceof ConversationAware)
        {
            ((ConversationAware)this.expirationEvaluator).setConversation(this);
        }
    }

    //just for a better performance to avoid frequent calls to the {@link #expirationEvaluator}
    private boolean active;

    /**
     * {@inheritDoc}
     */
    public boolean isActive()
    {
        return !isConversationExpired() && this.active;
    }

    /**
     * {@inheritDoc}
     */
    public boolean getActiveState()
    {
        return active;
    }

    /**
     * {@inheritDoc}
     */
    public void deactivate()
    {
        this.expirationEvaluator.expire();
        if (this.expirationEvaluator.isExpired())
        {
            endConversation();
        }
    }

    /**
     * {@inheritDoc}
     */
    public void close()
    {
        fireCloseConversationEvent();

        if(this.active)
        {
            endConversation();
        }
    }

    private void endConversation()
    {
        this.active = false;
        this.beanStorage.resetStorage();
        RequestCache.resetConversationCache();
    }

    /**
     * {@inheritDoc}
     */
    public void restart()
    {
        fireRestartConversationEvent();
        touchConversation();
        this.beanStorage.resetStorage();
    }

    /**
     * {@inheritDoc}
     */
    @SuppressWarnings({"unchecked"})
    public <T> T getBean(Class<T> key)
    {
        if (!this.active)
        {
            return null;
        }

        BeanEntry scopedBean = this.beanStorage.getBean(key);

        if (scopedBean == null)
        {
            return null;
        }

        touchConversation();

        return (T) scopedBean.getBeanInstance();
    }

    public <T> Set<Class<T>> getBeanSubGroup(Class<T> key)
    {
        return this.beanStorage.getBeanSubGroup(key);
    }

    /**
     * {@inheritDoc}
     */
    public <T> void addBean(BeanEntry<T> beanEntry)
    {
        //TODO check if conversation is active
        touchConversation();

        //TODO
        //noinspection unchecked
        this.beanStorage.addBean((BeanEntry<Serializable>) beanEntry);
    }

    /**
     * {@inheritDoc}
     */
    public <T> BeanEntry<T> removeBeanEntry(Class<T> type)
    {
        return (BeanEntry<T>) this.beanStorage.removeBean((Class<Serializable>) type);
    }

    private boolean isConversationExpired()
    {
        return this.expirationEvaluator.isExpired();
    }

    private void touchConversation()
    {
        this.active = true;

        this.expirationEvaluator.touch();
    }

    /**
     * just for test-cases (to expire a conversation manually)
     * @return current conversation-expiration-evaluator
     */
    public ConversationExpirationEvaluator getExpirationEvaluator()
    {
        return expirationEvaluator;
    }

    private void fireCloseConversationEvent()
    {
        if(this.closeConversationEventEnable)
        {
            this.beanManager.fireEvent(new CloseConversationEvent(this));
        }
    }

    private void fireRestartConversationEvent()
    {
        if(this.restartConversationEventEnable)
        {
            this.beanManager.fireEvent(new RestartConversationEvent(this));
        }
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public String toString()
    {
        StringBuilder result = new StringBuilder();

        result.append("\n*** conversation - start ***\n");
        result.append(this.conversationKey);

        result.append("\n");
        result.append("active state: ");
        result.append(getActiveState());
        result.append("\n");

        result.append(this.beanStorage);

        result.append("\n");
        result.append("expiration-evaluator: ");
        result.append(this.expirationEvaluator.getClass().getName());
        result.append("\n*** conversation - end ***");

        return result.toString();
    }
}
