/*
 * Copyright 2016 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.net.optical;

import static com.google.common.base.Preconditions.checkNotNull;
import static com.google.common.base.Preconditions.checkState;
import static org.slf4j.LoggerFactory.getLogger;

import java.util.Map;
import java.util.Optional;
import org.onlab.osgi.DefaultServiceDirectory;
import org.onosproject.net.Device;
import org.onosproject.net.Port;
import org.onosproject.net.device.DeviceService;
import org.onosproject.net.driver.AbstractBehaviour;
import org.onosproject.net.driver.DriverData;
import org.onosproject.net.optical.device.port.OchPortMapper;
import org.onosproject.net.optical.device.port.OduCltPortMapper;
import org.onosproject.net.optical.device.port.OmsPortMapper;
import org.onosproject.net.optical.device.port.OtuPortMapper;
import org.onosproject.net.optical.device.port.PortMapper;
import org.onosproject.net.optical.utils.ForwardingDevice;
import org.slf4j.Logger;

import com.google.common.annotations.Beta;
import com.google.common.base.MoreObjects;
import com.google.common.collect.ImmutableMap;

/**
 * Implementation of {@link OpticalDevice}.
 * <p>
 * Currently supports
 * <ul>
 *  <li> {@link OchPort}
 *  <li> {@link OmsPort}
 *  <li> {@link OduCltPort}
 *  <li> {@link OtuPort}
 * </ul>
 */
@Beta
public class DefaultOpticalDevice
        extends AbstractBehaviour
        implements OpticalDevice, ForwardingDevice {

    private static final Logger log = getLogger(DefaultOpticalDevice.class);

    // shared Port type handler map.
    // TODO Is there a use case, where we need to differentiate this map per Device?
    private static final Map<Class<? extends Port>, PortMapper<? extends Port>> MAPPERS
        = ImmutableMap.<Class<? extends Port>, PortMapper<? extends Port>>builder()
            .put(OchPort.class, new OchPortMapper())
            .put(OmsPort.class, new OmsPortMapper())
            .put(OduCltPort.class, new OduCltPortMapper())
            .put(OtuPort.class, new OtuPortMapper())
            // TODO add other optical port type here
            .build();



    // effectively final
    private Device delegate;

    // Default constructor required as a Behaviour.
    public DefaultOpticalDevice() {}

    @Override
    public Device delegate() {
        if (delegate == null) {
            // dirty work around.
            // wanted to pass delegate Device at construction,
            // but was not possible. A Behaviour requires no-arg constructor.
            checkState(data() != null, "DriverData must exist");
            DriverData data = data();
            DeviceService service = DefaultServiceDirectory.getService(DeviceService.class);
            delegate = checkNotNull(service.getDevice(data.deviceId()),
                                    "No Device found for %s", data.deviceId());
        }
        return delegate;
    }

    @Override
    public <T extends Port> boolean portIs(Port port, Class<T> portClass) {

        PortMapper<? extends Port> mapper = MAPPERS.get(portClass);
        if (mapper != null) {
            return mapper.is(port);
        }
        return false;
    }

    @Override
    public <T extends Port> Optional<T> portAs(Port port, Class<T> portClass) {
        PortMapper<? extends Port> mapper = MAPPERS.get(portClass);
        if (mapper != null) {
            return (Optional<T>) (mapper.as(port));
        }
        return Optional.empty();
    }

    @Override
    public Port port(Port port) {
        for (PortMapper<? extends Port> mapper : MAPPERS.values()) {
            if (mapper.is(port)) {
                return mapper.as(port).map(Port.class::cast).orElse(port);
            }
        }
        return port;
    }

    @Override
    public boolean equals(Object obj) {
        return delegate().equals(obj);
    }

    @Override
    public int hashCode() {
        return delegate().hashCode();
    }

    @Override
    public String toString() {
        return MoreObjects.toStringHelper(this)
                .add("delegate", delegate)
                .toString();
    }
}
