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

syntax = "proto3";

option java_multiple_files = true;
option java_package = "org.apache.skywalking.apm.network.register.v2";
option csharp_namespace = "SkyWalking.NetworkProtocol";

import "common/common.proto";

//register service for ApplicationCode, this service is called when service starts.
service Register {
    rpc doServiceRegister (Services) returns (ServiceRegisterMapping) {
    }

    rpc doServiceInstanceRegister (ServiceInstances) returns (ServiceInstanceRegisterMapping) {
    }

    rpc doEndpointRegister (Enpoints) returns (EndpointMapping) {
    }

    rpc doNetworkAddressRegister (NetAddresses) returns (NetAddressMapping) {
    }

    rpc doServiceAndNetworkAddressMappingRegister (ServiceAndNetworkAddressMappings) returns(Commands) {
    }
}

// Service register
message Services {
    repeated Service services = 1;
}

message Service {
    string serviceName = 1;
    repeated KeyStringValuePair tags = 3;
    repeated KeyStringValuePair properties = 4;
}

message ServiceRegisterMapping {
    repeated KeyIntValuePair services = 1;
}

// Service Instance register
message ServiceInstances {
    repeated ServiceInstance instances = 1;
}

message ServiceInstance {
    int32 serviceId = 1;
    string instanceUUID = 2;
    int64 time = 3;
    repeated KeyStringValuePair tags = 4;
    repeated KeyStringValuePair properties = 5;
}

message ServiceInstanceRegisterMapping {
    repeated KeyIntValuePair serviceInstances = 1;
}

// Network address register

// Only known use case is the language agent.
// Network address represents the ip/hostname:port, which is usually used at client side of RPC.
message NetAddresses {
    repeated string addresses = 1;
}

message NetAddressMapping {
    repeated KeyIntValuePair addressIds = 1;
}

// Endpint register
message Enpoints {
    repeated Endpoint endpoints = 1;
}

message Endpoint {
    int32 serviceId = 1;
    string endpointName = 2;
    repeated KeyStringValuePair tags = 3;
    repeated KeyStringValuePair properties = 4;
    // For endpoint
    // from DetectPoint is either `client` or `server`. No chance to be `proxy`.
    DetectPoint from = 5;
}

message EndpointMapping {
    repeated EndpointMappingElement elements = 1;
}

message EndpointMappingElement {
    int32 serviceId = 1;
    string endpointName = 2;
    int32 endpointId = 3;
    DetectPoint from = 4;
}

message ServiceAndNetworkAddressMappings {
    repeated ServiceAndNetworkAddressMapping mappings = 1;
}

message ServiceAndNetworkAddressMapping {
    int32 serviceId = 1;
    int32 serviceInstanceId = 2;
    string networkAddress = 3;
    int32 networkAddressId = 4;
}
