/*
 * 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.skywalking.oap.server.core.query;

import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import lombok.extern.slf4j.Slf4j;
import org.apache.skywalking.oap.server.library.util.StringUtil;
import org.apache.skywalking.oap.server.core.Const;
import org.apache.skywalking.oap.server.core.CoreModule;
import org.apache.skywalking.oap.server.core.analysis.IDManager;
import org.apache.skywalking.oap.server.core.analysis.manual.networkalias.NetworkAddressAlias;
import org.apache.skywalking.oap.server.core.cache.NetworkAddressAliasCache;
import org.apache.skywalking.oap.server.core.config.IComponentLibraryCatalogService;
import org.apache.skywalking.oap.server.core.query.type.Call;
import org.apache.skywalking.oap.server.core.query.type.Node;
import org.apache.skywalking.oap.server.core.query.type.Topology;
import org.apache.skywalking.oap.server.core.source.DetectPoint;
import org.apache.skywalking.oap.server.library.module.ModuleManager;

@Slf4j
class ServiceTopologyBuilder {
    private final IComponentLibraryCatalogService componentLibraryCatalogService;
    private final NetworkAddressAliasCache networkAddressAliasCache;
    private final String userID;

    ServiceTopologyBuilder(ModuleManager moduleManager) {
        this.componentLibraryCatalogService = moduleManager.find(CoreModule.NAME)
                                                           .provider()
                                                           .getService(IComponentLibraryCatalogService.class);
        this.networkAddressAliasCache = moduleManager.find(CoreModule.NAME)
                                                     .provider()
                                                     .getService(NetworkAddressAliasCache.class);
        this.userID = IDManager.ServiceID.buildId(Const.USER_SERVICE_NAME, false);
    }

    Topology build(List<Call.CallDetail> serviceRelationClientCalls, List<Call.CallDetail> serviceRelationServerCalls) {

        Map<String, Node> nodes = new HashMap<>();
        List<Call> calls = new LinkedList<>();
        HashMap<String, Call> callMap = new HashMap<>();

        for (Call.CallDetail clientCall : serviceRelationClientCalls) {
            final IDManager.ServiceID.ServiceIDDefinition sourceService = IDManager.ServiceID.analysisId(
                clientCall.getSource());
            String sourceServiceId = clientCall.getSource();
            IDManager.ServiceID.ServiceIDDefinition destService = IDManager.ServiceID.analysisId(
                clientCall.getTarget());
            String targetServiceId = clientCall.getTarget();

            /*
             * Use the alias name to make topology relationship accurate.
             */
            if (networkAddressAliasCache.get(destService.getName()) != null) {
                /*
                 * If alias exists, mean this network address is representing a real service.
                 */
                final NetworkAddressAlias networkAddressAlias = networkAddressAliasCache.get(destService.getName());
                destService = IDManager.ServiceID.analysisId(
                    networkAddressAlias.getRepresentServiceId());
                targetServiceId = IDManager.ServiceID.buildId(destService.getName(), true);
            }

            /*
             * Set the conjectural node type.
             */
            if (!nodes.containsKey(targetServiceId)) {
                final Node conjecturalNode = buildNode(targetServiceId, destService);
                nodes.put(targetServiceId, conjecturalNode);
                if (!conjecturalNode.isReal() && StringUtil.isEmpty(conjecturalNode.getType())) {
                    conjecturalNode.setType(
                        componentLibraryCatalogService.getServerNameBasedOnComponent(clientCall.getComponentId()));
                }
            }

            if (!nodes.containsKey(sourceServiceId)) {
                nodes.put(sourceServiceId, buildNode(sourceServiceId, sourceService));
            }

            final String relationId = IDManager.ServiceID.buildRelationId(
                new IDManager.ServiceID.ServiceRelationDefine(sourceServiceId, targetServiceId));

            if (!callMap.containsKey(relationId)) {
                Call call = new Call();

                callMap.put(relationId, call);
                call.setSource(sourceServiceId);
                call.setTarget(targetServiceId);
                call.setId(relationId);
                call.addDetectPoint(DetectPoint.CLIENT);
                call.addSourceComponent(componentLibraryCatalogService.getComponentName(clientCall.getComponentId()));
                calls.add(call);
            }
        }

        for (Call.CallDetail serverCall : serviceRelationServerCalls) {
            final IDManager.ServiceID.ServiceIDDefinition sourceService = IDManager.ServiceID.analysisId(
                serverCall.getSource());
            IDManager.ServiceID.ServiceIDDefinition destService = IDManager.ServiceID.analysisId(
                serverCall.getTarget());

            /*
             * Create the client node if it hasn't been created in client side call.
             */
            Node clientSideNode = nodes.get(serverCall.getSource());
            if (clientSideNode == null) {
                clientSideNode = buildNode(serverCall.getSource(), sourceService);
                nodes.put(serverCall.getSource(), clientSideNode);
            }
            /*
             * conjectural node type.
             */
            if (!clientSideNode.isReal()) {
                clientSideNode.setType(
                    componentLibraryCatalogService.getServerNameBasedOnComponent(serverCall.getComponentId()));
            }
            /*
             * Format the User name type.
             */
            if (userID.equals(serverCall.getSource())) {
                nodes.get(userID).setType(Const.USER_SERVICE_NAME.toUpperCase());
            }
            /*
             * Create the server node if it hasn't been created.
             */
            if (!nodes.containsKey(serverCall.getTarget())) {
                final Node node = buildNode(serverCall.getTarget(), destService);
                nodes.put(serverCall.getTarget(), node);
            }
            /*
             * Set the node type due to service side component id has higher priority
             */
            final Node serverSideNode = nodes.get(serverCall.getTarget());
            serverSideNode.setType(
                componentLibraryCatalogService.getComponentName(serverCall.getComponentId()));

            if (!callMap.containsKey(serverCall.getId())) {
                Call call = new Call();
                callMap.put(serverCall.getId(), call);
                call.setSource(serverCall.getSource());
                call.setTarget(serverCall.getTarget());
                call.setId(serverCall.getId());
                call.addDetectPoint(DetectPoint.SERVER);
                call.addTargetComponent(componentLibraryCatalogService.getComponentName(serverCall.getComponentId()));
                calls.add(call);
            } else {
                Call call = callMap.get(serverCall.getId());
                call.addDetectPoint(DetectPoint.SERVER);
                call.addTargetComponent(componentLibraryCatalogService.getComponentName(serverCall.getComponentId()));
            }
        }

        Topology topology = new Topology();
        topology.getCalls().addAll(calls);
        topology.getNodes().addAll(nodes.values());
        return topology;
    }

    private Node buildNode(String sourceId, IDManager.ServiceID.ServiceIDDefinition sourceService) {
        Node serviceNode = new Node();
        serviceNode.setId(sourceId);
        serviceNode.setName(sourceService.getName());
        serviceNode.setReal(sourceService.isReal());
        return serviceNode;
    }
}
