2016-07-22 27 views
3
  1. 假设我有服务架构集群中托管的服务A和B.他们分别在端口7001和7002监听(在集群内)。
  2. 假设我将服务结构负载平衡器配置为侦听端口8001,并将请求转发到服务A的端口7001(集群内),并侦听端口8002并将请求转发到端口7002(集群内)服务B.
  3. 假设我为服务A和B配置API管理,并将请求路由到负载均衡器上的相应端口。
  4. 这一切都有效。
  5. 现在,我不想为每个服务手动映射url路由,而是动态发现服务结构中托管的服务(从API管理),并在运行时动态发送请求。
  6. 要做到这一点,我知道我必须编写一个策略(最有可能用C#)从某处查找此信息。
  7. 但我不确定要查询哪些查找负载均衡端口和托管在服务结构集群中的服务。
  8. 我想在同一个服务结构集群中创建另一个服务C并使用它(来自API管理)来提供集群的内部信息。
  9. 但我无法找到查找本地服务端口信息或负载均衡服务端口信息的方法。

我该怎么办?如何从API管理中动态发现托管在服务结构中的服务?

回答

14

以下是发现在集群中运行的服务和端点的方法。 (请记住,你需要监视变化太大。)

private static void ListEndpoints() 
{ 
    var resolver = ServicePartitionResolver.GetDefault(); 
    var fabricClient = new FabricClient(); 
    var apps = fabricClient.QueryManager.GetApplicationListAsync().Result; 
    foreach (var app in apps) 
    { 
     Console.WriteLine($"Discovered application:'{app.ApplicationName}"); 

     var services = fabricClient.QueryManager.GetServiceListAsync(app.ApplicationName).Result; 
     foreach (var service in services) 
     { 
      Console.WriteLine($"Discovered Service:'{service.ServiceName}"); 

      var partitions = fabricClient.QueryManager.GetPartitionListAsync(service.ServiceName).Result; 
      foreach (var partition in partitions) 
      { 
       Console.WriteLine($"Discovered Service Partition:'{partition.PartitionInformation.Kind} {partition.PartitionInformation.Id}"); 


       ServicePartitionKey key; 
       switch (partition.PartitionInformation.Kind) 
       { 
        case ServicePartitionKind.Singleton: 
         key = ServicePartitionKey.Singleton; 
         break; 
        case ServicePartitionKind.Int64Range: 
         var longKey = (Int64RangePartitionInformation)partition.PartitionInformation; 
         key = new ServicePartitionKey(longKey.LowKey); 
         break; 
        case ServicePartitionKind.Named: 
         var namedKey = (NamedPartitionInformation)partition.PartitionInformation; 
         key = new ServicePartitionKey(namedKey.Name); 
         break; 
        default: 
         throw new ArgumentOutOfRangeException("partition.PartitionInformation.Kind"); 
       } 
       var resolved = resolver.ResolveAsync(service.ServiceName, key, CancellationToken.None).Result; 
       foreach (var endpoint in resolved.Endpoints) 
       { 
        Console.WriteLine($"Discovered Service Endpoint:'{endpoint.Address}"); 
       } 
      } 
     } 
    } 
} 

可以使用PowerShell和负载均衡器通信:

Get-AzureRmLoadBalancer 

最后你需要想出一个办法将负载均衡后端端口与您自己的服务端点进行匹配。

+0

我已经离开了一段时间。这太棒了。谢谢。 – Raghu

+0

虽然好,但这并不反映因缩放而导致的变化。 (如果您运行此代码,请打开资源管理器(端口19080)并选择将服务扩展到更多或更少的实例,然后再次运行此代码(但不要重新启动正在运行的服务),它将返回以前的端点。 – Vaccano