/*
 * 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.vtnrsc;

import static com.google.common.base.Preconditions.checkNotNull;

import java.util.Objects;

import org.onlab.packet.IpPrefix;

import com.google.common.base.MoreObjects;

/**
 * Provides Default flow classifier.
 */
public final class DefaultFlowClassifier implements FlowClassifier {

    private final FlowClassifierId flowClassifierId;
    private final TenantId tenantId;
    private final String name;
    private final String description;
    private final String etherType;
    private final String protocol;
    private final int minSrcPortRange;
    private final int maxSrcPortRange;
    private final int minDstPortRange;
    private final int maxDstPortRange;
    private final IpPrefix srcIpPrefix;
    private final IpPrefix dstIpPrefix;
    private final VirtualPortId srcPort;
    private final VirtualPortId dstPort;
    private static final int NULL_PORT = 0;
    private static final String FLOW_CLASSIFIER_ID_NOT_NULL = "FlowClassifier id can not be null.";
    private static final String TENANT_ID_NOT_NULL = "Tenant id can not be null.";
    private static final String NAME_NOT_NULL = "Name can not be null.";
    private static final String ETHER_TYPE_NOT_NULL = "Ether Type can not be null.";

    /**
     * Constructor to create default flow classifier.
     *
     * @param flowClassifierId      flow classifier Id
     * @param tenantId              Tenant ID
     * @param name                  flow classifier name
     * @param description           flow classifier description
     * @param etherType             etherType
     * @param protocol              IP protocol
     * @param minSrcPortRange       Minimum Source port range
     * @param maxSrcPortRange       Maximum Source port range
     * @param minDstPortRange       Minimum destination port range
     * @param maxDstPortRange       Maximum destination port range
     * @param srcIpPrefix           Source IP prefix
     * @param dstIpPrefix           destination IP prefix
     * @param srcPort               Source VirtualPort
     * @param dstPort               destination VirtualPort
     */
    private DefaultFlowClassifier(FlowClassifierId flowClassifierId, TenantId tenantId, String name,
            String description, String etherType, String protocol, int minSrcPortRange, int maxSrcPortRange,
            int minDstPortRange, int maxDstPortRange, IpPrefix srcIpPrefix, IpPrefix dstIpPrefix,
            VirtualPortId srcPort, VirtualPortId dstPort) {
        this.flowClassifierId = flowClassifierId;
        this.tenantId = tenantId;
        this.name = name;
        this.description = description;
        this.etherType = etherType;
        this.protocol = protocol;
        this.minSrcPortRange = minSrcPortRange;
        this.maxSrcPortRange = maxSrcPortRange;
        this.minDstPortRange = minDstPortRange;
        this.maxDstPortRange = maxDstPortRange;
        this.srcIpPrefix = srcIpPrefix;
        this.dstIpPrefix = dstIpPrefix;
        this.srcPort = srcPort;
        this.dstPort = dstPort;
    }

    @Override
    public FlowClassifierId flowClassifierId() {
        return flowClassifierId;
    }

    @Override
    public TenantId tenantId() {
        return tenantId;
    }

    @Override
    public String name() {
        return name;
    }

    @Override
    public String description() {
        return description;
    }

    @Override
    public String etherType() {
        return etherType;
    }

    @Override
    public String protocol() {
        return protocol;
    }

    @Override
    public int minSrcPortRange() {
        return minSrcPortRange;
    }

    @Override
    public int maxSrcPortRange() {
        return maxSrcPortRange;
    }

    @Override
    public int minDstPortRange() {
        return minDstPortRange;
    }

    @Override
    public int maxDstPortRange() {
        return maxDstPortRange;
    }

    @Override
    public IpPrefix srcIpPrefix() {
        return srcIpPrefix;
    }

    @Override
    public IpPrefix dstIpPrefix() {
        return dstIpPrefix;
    }

    @Override
    public VirtualPortId srcPort() {
        return srcPort;
    }

    @Override
    public VirtualPortId dstPort() {
        return dstPort;
    }

    /**
     * Builder class for constructing Flow classifier.
     */
    public static class Builder implements FlowClassifier.Builder {

        private FlowClassifierId flowClassifierId;
        private TenantId tenantId;
        private String name;
        private String description;
        private boolean isFlowClassifierDescriptionSet = false;
        private String etherType;
        private String protocol;
        private boolean isProtocolSet = false;
        private int minSrcPortRange;
        private boolean isMinSrcPortRangeSet = false;
        private int maxSrcPortRange;
        private boolean isMaxSrcPortRangeSet = false;
        private int minDstPortRange;
        private boolean isMinDstPortRangeSet = false;
        private int maxDstPortRange;
        private boolean isMaxDstPortRangeSet = false;
        private IpPrefix srcIpPrefix;
        private boolean isSrcIpPrefixSet = false;
        private IpPrefix dstIpPrefix;
        private boolean isDstIpPrefixSet = false;
        private VirtualPortId srcPort;
        private boolean isSrcPortSet = false;
        private VirtualPortId dstPort;
        private boolean isDstPortSet = false;

        @Override
        public FlowClassifier build() {

            checkNotNull(flowClassifierId, FLOW_CLASSIFIER_ID_NOT_NULL);
            checkNotNull(tenantId, TENANT_ID_NOT_NULL);
            checkNotNull(name, NAME_NOT_NULL);
            checkNotNull(etherType, ETHER_TYPE_NOT_NULL);
            String description = null;
            String protocol = null;
            int minSrcPortRange = NULL_PORT;
            int maxSrcPortRange = NULL_PORT;
            int minDstPortRange = NULL_PORT;
            int maxDstPortRange = NULL_PORT;
            IpPrefix srcIpPrefix = null;
            IpPrefix dstIpPrefix = null;
            VirtualPortId srcPort = null;
            VirtualPortId dstPort = null;

            if (isFlowClassifierDescriptionSet) {
                description = this.description;
            }
            if (isProtocolSet) {
                protocol = this.protocol;
            }
            if (isMinSrcPortRangeSet) {
                minSrcPortRange = this.minSrcPortRange;
            }
            if (isMaxSrcPortRangeSet) {
                maxSrcPortRange = this.maxSrcPortRange;
            }
            if (isMinDstPortRangeSet) {
                minDstPortRange = this.minDstPortRange;
            }
            if (isMaxDstPortRangeSet) {
                maxDstPortRange = this.maxDstPortRange;
            }
            if (isSrcIpPrefixSet) {
                srcIpPrefix = this.srcIpPrefix;
            }
            if (isDstIpPrefixSet) {
                dstIpPrefix = this.dstIpPrefix;
            }
            if (isSrcPortSet) {
                srcPort = this.srcPort;
            }
            if (isDstPortSet) {
                dstPort = this.dstPort;
            }

            return new DefaultFlowClassifier(flowClassifierId, tenantId, name, description, etherType, protocol,
                    minSrcPortRange, maxSrcPortRange, minDstPortRange, maxDstPortRange, srcIpPrefix, dstIpPrefix,
                    srcPort, dstPort);
        }

        @Override
        public Builder setFlowClassifierId(FlowClassifierId flowClassifierId) {
            this.flowClassifierId = flowClassifierId;
            return this;
        }

        @Override
        public Builder setTenantId(TenantId tenantId) {
            this.tenantId = tenantId;
            return this;
        }

        @Override
        public Builder setName(String name) {
            this.name = name;
            return this;
        }

        @Override
        public Builder setDescription(String description) {
            this.description = description;
            this.isFlowClassifierDescriptionSet = true;
            return this;
        }

        @Override
        public Builder setEtherType(String etherType) {
            this.etherType = etherType;
            return this;
        }

        @Override
        public Builder setProtocol(String protocol) {
            this.protocol = protocol;
            this.isProtocolSet = true;
            return this;
        }

        @Override
        public Builder setMinSrcPortRange(int minSrcPortRange) {
            this.minSrcPortRange = minSrcPortRange;
            this.isMinSrcPortRangeSet = true;
            return this;
        }

        @Override
        public Builder setMaxSrcPortRange(int maxSrcPortRange) {
            this.maxSrcPortRange = maxSrcPortRange;
            this.isMaxSrcPortRangeSet = true;
            return this;
        }

        @Override
        public Builder setMinDstPortRange(int minDstPortRange) {
            this.minDstPortRange = minDstPortRange;
            this.isMinDstPortRangeSet = true;
            return this;
        }

        @Override
        public Builder setMaxDstPortRange(int maxDstPortRange) {
            this.maxDstPortRange = maxDstPortRange;
            this.isMaxDstPortRangeSet = true;
            return this;
        }

        @Override
        public Builder setSrcIpPrefix(IpPrefix srcIpPrefix) {
            this.srcIpPrefix = srcIpPrefix;
            this.isSrcIpPrefixSet = true;
            return this;
        }

        @Override
        public Builder setDstIpPrefix(IpPrefix dstIpPrefix) {
            this.dstIpPrefix = dstIpPrefix;
            this.isDstIpPrefixSet = true;
            return this;
        }

        @Override
        public Builder setSrcPort(VirtualPortId srcPort) {
            this.srcPort = srcPort;
            this.isSrcPortSet = true;
            return this;
        }

        @Override
        public Builder setDstPort(VirtualPortId dstPort) {
            this.dstPort = dstPort;
            this.isDstPortSet = true;
            return this;
        }
    }

    @Override
    public int hashCode() {
        return Objects.hash(flowClassifierId, tenantId, name, description, etherType, protocol, minSrcPortRange,
                maxSrcPortRange, minDstPortRange, maxDstPortRange, srcIpPrefix, dstIpPrefix, srcPort, dstPort);
    }

    @Override
    public boolean equals(Object obj) {
        if (this == obj) {
            return true;
        }
        if (obj instanceof DefaultFlowClassifier) {
            DefaultFlowClassifier other = (DefaultFlowClassifier) obj;
            return Objects.equals(this.flowClassifierId, other.flowClassifierId)
                    && Objects.equals(this.tenantId, other.tenantId)
                    && Objects.equals(this.name, other.name)
                    && Objects.equals(this.description, other.description)
                    && Objects.equals(this.etherType, other.etherType)
                    && Objects.equals(this.protocol, other.protocol)
                    && Objects.equals(this.minSrcPortRange, other.minSrcPortRange)
                    && Objects.equals(this.maxSrcPortRange, other.maxSrcPortRange)
                    && Objects.equals(this.minDstPortRange, other.minDstPortRange)
                    && Objects.equals(this.maxDstPortRange, other.maxDstPortRange)
                    && Objects.equals(this.srcIpPrefix, other.srcIpPrefix)
                    && Objects.equals(this.dstIpPrefix, other.dstIpPrefix)
                    && Objects.equals(this.srcPort, other.srcPort)
                    && Objects.equals(this.dstPort, other.dstPort);
        }
        return false;
    }

    @Override
    public boolean exactMatch(FlowClassifier flowClassifier) {
        return this.equals(flowClassifier)
                && Objects.equals(this.flowClassifierId, flowClassifier.flowClassifierId())
                && Objects.equals(this.tenantId, flowClassifier.tenantId())
                && Objects.equals(this.name, flowClassifier.name())
                && Objects.equals(this.description, flowClassifier.description())
                && Objects.equals(this.etherType, flowClassifier.etherType())
                && Objects.equals(this.protocol, flowClassifier.protocol())
                && Objects.equals(this.minSrcPortRange, flowClassifier.minSrcPortRange())
                && Objects.equals(this.maxSrcPortRange, flowClassifier.maxSrcPortRange())
                && Objects.equals(this.minDstPortRange, flowClassifier.minDstPortRange())
                && Objects.equals(this.maxDstPortRange, flowClassifier.maxDstPortRange())
                && Objects.equals(this.srcIpPrefix, flowClassifier.srcIpPrefix())
                && Objects.equals(this.dstIpPrefix, flowClassifier.dstIpPrefix())
                && Objects.equals(this.srcPort, flowClassifier.srcPort())
                && Objects.equals(this.dstPort, flowClassifier.dstPort());
    }

    @Override
    public String toString() {
        return MoreObjects.toStringHelper(getClass())
                .add("FlowClassifierId", flowClassifierId)
                .add("TenantId", tenantId)
                .add("Name", name)
                .add("Description", description)
                .add("String", etherType)
                .add("Protocol", protocol)
                .add("MinSrcPortRange", minSrcPortRange)
                .add("MaxSrcPortRange", maxSrcPortRange)
                .add("MinDstPortRange", minDstPortRange)
                .add("MaxDstPortRange", maxDstPortRange)
                .add("SrcIpPrefix", srcIpPrefix)
                .add("DstIpPrefix", dstIpPrefix)
                .add("SrcPort", srcPort)
                .add("DstPort", dstPort)
                .toString();
    }
}
