/*
 * Copyright 2017-present Open Networking Foundation
 *
 * 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.mapping.cli;

import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.node.ArrayNode;
import com.fasterxml.jackson.databind.node.ObjectNode;
import org.apache.karaf.shell.commands.Argument;
import org.apache.karaf.shell.commands.Command;
import org.apache.karaf.shell.commands.Option;
import org.onosproject.cli.AbstractShellCommand;
import org.onosproject.mapping.MappingEntry;
import org.onosproject.mapping.MappingKey;
import org.onosproject.mapping.MappingTreatment;
import org.onosproject.mapping.MappingValue;
import org.onosproject.mapping.MappingService;
import org.onosproject.mapping.MappingStore;
import org.onosproject.net.Device;
import org.onosproject.net.DeviceId;
import org.onosproject.net.device.DeviceService;

import java.util.List;

import static com.google.common.collect.Lists.newArrayList;

/**
 * A command for querying mapping information.
 */
@Command(scope = "onos", name = "mappings",
        description = "Lists mappings")
public class MappingsListCommand extends AbstractShellCommand {

    private static final String DB = "database";
    private static final String CACHE = "cache";

    private static final String SUMMARY_FORMAT = "deviceId=%s, mappingCount=%d";
    private static final String MAPPING_ID_FORMAT = "  id=%s";
    private static final String MAPPING_STATE_FORMAT = "  state=%s";
    private static final String MAPPING_KEY_FORMAT = "  key=%s";
    private static final String MAPPING_VALUE_FORMAT = "  value=";
    private static final String MAPPING_ACTION_FORMAT = "    action=%s";
    private static final String MAPPING_TREATMENTS_FORMAT = "    treatments=";
    private static final String MAPPING_TREATMENT_LONG_FORMAT =
            "      address=%s, instructions=%s";
    private static final String MAPPING_TREATMENT_SHORT_FORMAT = "      %s";
    private static final String JSON_FORMAT = "%s";

    private static final String TYPE_NOT_NULL = "Mapping store type should not be null";
    private static final String TYPE_ILLEGAL = "Mapping store type is not correct";

    @Argument(index = 0, name = "type",
            description = "Shows mappings with specified type",
            required = true, multiValued = false)
    private String type = null;

    @Argument(index = 1, name = "deviceId", description = "Device identity",
            required = false, multiValued = false)
    private String deviceId = null;

    @Option(name = "-s", aliases = "--short",
            description = "Print more succinct output for each mapping",
            required = false, multiValued = false)
    private boolean shortOutput = false;

    private MappingService mappingService =
            AbstractShellCommand.get(MappingService.class);
    private List<MappingEntry> mappings;

    @Override
    protected void execute() {

        MappingStore.Type typeEnum = getTypeEnum(type);

        DeviceService deviceService = get(DeviceService.class);
        Iterable<Device> devices = deviceService.getDevices();

        if (outputJson()) {
            print(JSON_FORMAT, json(typeEnum, devices));
        } else {
            if (deviceId != null) {
                mappings = newArrayList(mappingService.getMappingEntries(typeEnum,
                        DeviceId.deviceId(deviceId)));
                printMappings(DeviceId.deviceId(deviceId), mappings);

            } else {

                for (Device d : devices) {
                    mappings = newArrayList(mappingService.getMappingEntries(typeEnum, d.id()));
                    printMappings(d.id(), mappings);
                }
            }
        }
    }

    /**
     * Prints out mapping information.
     *
     * @param deviceId device identifier
     * @param mappings a collection of mapping
     */
    private void printMappings(DeviceId deviceId, List<MappingEntry> mappings) {

        print(SUMMARY_FORMAT, deviceId, mappings.size());

        for (MappingEntry m : mappings) {
            print(MAPPING_ID_FORMAT, Long.toHexString(m.id().value()));
            print(MAPPING_STATE_FORMAT, m.state().name());
            print(MAPPING_KEY_FORMAT, printMappingKey(m.key()));
            printMappingValue(m.value());
        }
    }

    /**
     * Prints out mapping key.
     *
     * @param key mapping key
     * @return string format of mapping key
     */
    private String printMappingKey(MappingKey key) {
        StringBuilder builder = new StringBuilder();

        if (key.address() != null) {
            builder.append(key.address().toString());
        }

        return builder.toString();
    }

    /**
     * Prints out mapping value.
     *
     * @param value mapping value
     * @return string format of mapping value
     */
    private void printMappingValue(MappingValue value) {

        print(MAPPING_VALUE_FORMAT);

        if (value.action() != null) {
            print(MAPPING_ACTION_FORMAT, value.action().toString());
        }

        if (!value.treatments().isEmpty()) {
            print(MAPPING_TREATMENTS_FORMAT);
            for (MappingTreatment treatment : value.treatments()) {
                printMappingTreatment(treatment);
            }
        }

    }

    /**
     * Prints out mapping treatment.
     *
     * @param treatment mapping treatment
     * @return string format of mapping treatment
     */
    private void printMappingTreatment(MappingTreatment treatment) {
        if (treatment != null) {
            if (shortOutput) {
                print(MAPPING_TREATMENT_SHORT_FORMAT, treatment.address());
            } else {
                print(MAPPING_TREATMENT_LONG_FORMAT, treatment.address(),
                        treatment.instructions());
            }
        }
    }

    /**
     * Returns corresponding type enumeration based on the given
     * string formatted type.
     *
     * @param type string formatted type
     * @return type enumeration
     */
    private MappingStore.Type getTypeEnum(String type) {

        if (type == null) {
            throw new IllegalArgumentException(TYPE_NOT_NULL);
        }

        switch (type) {
            case DB:
                return MappingStore.Type.MAP_DATABASE;
            case CACHE:
                return MappingStore.Type.MAP_CACHE;
            default:
                throw new IllegalArgumentException(TYPE_ILLEGAL);
        }
    }

    /**
     * Generates JSON object with the mappings of the given device.
     *
     * @param mapper   object mapper
     * @param device   device
     * @param mappings a collection of mappings
     * @return JSON object
     */
    private ObjectNode json(ObjectMapper mapper, Device device, List<MappingEntry> mappings) {
        ObjectNode result = mapper.createObjectNode();
        ArrayNode array = mapper.createArrayNode();

        mappings.forEach(mapping -> array.add(jsonForEntity(mapping, MappingEntry.class)));

        result.put("device", device.id().toString())
                .put("mappingCount", mappings.size())
                .set("mappings", array);
        return result;
    }

    /**
     * Generates JSON object with the mappings of all devices.
     *
     * @param type    mapping store type
     * @param devices a collection of devices
     * @return JSON object
     */
    private JsonNode json(MappingStore.Type type, Iterable<Device> devices) {
        ObjectMapper mapper = new ObjectMapper();
        ArrayNode result = mapper.createArrayNode();
        for (Device device : devices) {
            result.add(json(mapper, device,
                    newArrayList(mappingService.getMappingEntries(type, device.id()))));
        }
        return result;
    }
}
