/*
 * Copyright 2015-present Open Networking Laboratory
 *
 * Licensed 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.onosproject.store.core.impl;

import static org.slf4j.LoggerFactory.getLogger;


import java.util.Map;
import java.util.Set;


import org.apache.felix.scr.annotations.Activate;
import org.apache.felix.scr.annotations.Component;
import org.apache.felix.scr.annotations.Deactivate;
import org.apache.felix.scr.annotations.Reference;
import org.apache.felix.scr.annotations.ReferenceCardinality;
import org.apache.felix.scr.annotations.Service;
import org.onosproject.core.ApplicationId;
import org.onosproject.core.ApplicationIdStore;
import org.onosproject.core.DefaultApplicationId;
import org.onosproject.store.serializers.KryoNamespaces;
import org.onosproject.store.service.AtomicCounter;
import org.onosproject.store.service.ConsistentMap;
import org.onosproject.store.service.MapEvent;
import org.onosproject.store.service.MapEventListener;
import org.onosproject.store.service.Serializer;
import org.onosproject.store.service.StorageService;
import org.slf4j.Logger;


import com.google.common.collect.ImmutableSet;
import com.google.common.collect.Maps;

/**
 * ApplicationIdStore implementation on top of {@code AtomicCounter}
 * and {@code ConsistentMap} primitives.
 */
@Component(immediate = true)
@Service
public class DistributedApplicationIdStore implements ApplicationIdStore {

    private final Logger log = getLogger(getClass());

    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
    protected StorageService storageService;

    private AtomicCounter appIdCounter;
    private ConsistentMap<String, ApplicationId> registeredIds;
    private Map<Short, ApplicationId> idToAppIdCache = Maps.newConcurrentMap();
    private MapEventListener<String, ApplicationId> mapEventListener = event -> {
        if (event.type() == MapEvent.Type.INSERT) {
            idToAppIdCache.put(event.newValue().value().id(), event.newValue().value());
        }
    };

    @Activate
    public void activate() {
        appIdCounter = storageService.getAtomicCounter("onos-app-id-counter");

        registeredIds = storageService.<String, ApplicationId>consistentMapBuilder()
                .withName("onos-app-ids")
                .withSerializer(Serializer.using(KryoNamespaces.API))
                .withRelaxedReadConsistency()
                .build();

        primeIdToAppIdCache();
        registeredIds.addListener(mapEventListener);

        log.info("Started");
    }

    @Deactivate
    public void deactivate() {
        registeredIds.removeListener(mapEventListener);
        log.info("Stopped");
    }

    @Override
    public Set<ApplicationId> getAppIds() {
        return ImmutableSet.copyOf(registeredIds.asJavaMap().values());
    }

    @Override
    public ApplicationId getAppId(Short id) {
        if (!idToAppIdCache.containsKey(id)) {
            primeIdToAppIdCache();
        }
        return idToAppIdCache.get(id);
    }

    @Override
    public ApplicationId getAppId(String name) {
        return registeredIds.asJavaMap().get(name);
    }

    @Override
    public ApplicationId registerApplication(String name) {
        ApplicationId exisitingAppId = registeredIds.asJavaMap().get(name);
        if (exisitingAppId == null) {
            ApplicationId newAppId = new DefaultApplicationId((int) appIdCounter.incrementAndGet(), name);
            exisitingAppId = registeredIds.asJavaMap().putIfAbsent(name, newAppId);
            return exisitingAppId == null ? newAppId : exisitingAppId;
        } else {
            return exisitingAppId;
        }
    }

    private void primeIdToAppIdCache() {
        registeredIds.asJavaMap()
                     .values()
                     .forEach(appId -> {
                         idToAppIdCache.putIfAbsent(appId.id(), appId);
                     });
    }
}
