nacos实现Java和.NetCore的服务注册和调用
用nacos作为服务注册中心,如何注册.NetCore服务,如何在Java中调用.NetCore服务呢?可以分为下面几个步骤:
0.运行nacos
1.开发.net core服务,然后调用nacos提供的.net core sdk注册服务。
2.开发Java服务,然后注册服务。
3.用RestTemplate调用.net core服务。
4.用OpenFeign调用服务
下面来看具体步骤:
0.参考我之前的文章
分布式配置nacos搭建踩坑指南(下)
,首先运行nacos.
1.首先开发一个.net core web api,我们返回的数据是天气预报消息,新建一个WeatherForecastController,代码如下:
usingMicrosoft.AspNetCore.Mvc;usingMicrosoft.Extensions.Logging;usingSystem;usingSystem.Collections.Generic;usingSystem.Linq;usingSystem.Threading.Tasks;
namespaceWebApi.Controllers
{
[ApiController]
[Route("[controller]")]public classWeatherForecastController : ControllerBase
{private static readonly string[] Summaries = new[]
{"Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"};
private readonly ILogger<WeatherForecastController>_logger;
public WeatherForecastController(ILogger<WeatherForecastController>logger)
{
_logger=logger;
}
[HttpGet]public IEnumerable<WeatherForecast>Get()
{var rng = newRandom();return Enumerable.Range(1, 5).Select(index => newWeatherForecast
{
Date=DateTime.Now.AddDays(index),
TemperatureC= rng.Next(-20, 55),
Summary=Summaries[rng.Next(Summaries.Length)]
})
.ToArray();
}//public String Get()//{//return "sunny";//}
}
}
然后设置好访问的url,在launchSettings.json的修改 "applicationUrl": "http://192.168.1.110:5000",注意这里去掉了https://192.168.1.110:5001,是为了避免在后面Java调用时需要证书的麻烦。
最后我们在cmd中输入dotnet run,当服务正常运行起来后,在浏览器中输入:http://192.168.1.110:5000/weatherforecast,发现成功返回天气数据,格式为json,截图如下:
2.net core项目中引入nuget包:nacos-sdk-csharp,截图如下:
3.调用nacos-sdk-csharp,进行服务注册,代码如下:
usingSystem;usingMicrosoft.Extensions.DependencyInjection;usingNacos.V2;usingNacos.V2.DependencyInjection;usingSystem.Collections.Generic;usingSystem.Threading.Tasks;namespaceNacosDiscoveryProviderNetCoreTest1
{classProgram
{static async Task Main(string[] args)
{string serverAddr = "http://localhost:8848";string dataId = "config2";string group = "DEFAULT_GROUP";
IServiceCollection services= newServiceCollection();//register service services.AddNacosV2Naming(
x=>{
x.ServerAddresses= new List<string>() { serverAddr };//x.ConfigUseRpc = true;
}
);
IServiceProvider serviceProvider=services.BuildServiceProvider();var namingSvc = serviceProvider.GetService<INacosNamingService>();await namingSvc.RegisterInstance("weatherforecast", "192.168.1.110", 5000);
Console.WriteLine(Newtonsoft.Json.JsonConvert.SerializeObject(await namingSvc.GetAllInstances("weatherforecast")));
Console.ReadKey();
}
}
}
我们进入nacos后台,如果服务注册成功,我们就会在服务列表中看到weatherforecast服务了,如下所示:
有两个地方必须切记注意:
1).namingSvc.RegisterInstance("weatherforecast", "192.168.1.110", 5000);是一句很关键的代码,意思是注册一个名为weatherforecast,地址为:192.168.1.110,端口为:5000的服务。
2)launchSettings.json里的applicationUrl必须去掉包含https的设置,只保留http的设置,即只保留:"applicationUrl": "http://192.168.1.110:5000",否则在Java中调用会报证书错误。
4.参考
nacos服务注册
,利用阿里巴巴Spring boot脚手架,引入:spring-boot-starter-web,spring-cloud-starter-alibaba-nacos-discovery,spring-cloud-starter,spring-boot-starter-test,spring-cloud-starter-loadbalancer,spring-cloud-starter-openfeign。完整的pom如下:
<?xml version="1.0" encoding="UTF-8"?> <projectxmlns="http://maven.apache.org/POM/4.0.0"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>2.6.11</version> <relativePath/> <!--lookup parent from repository--> </parent> <groupId>com.alibaba.cloud</groupId> <artifactId>nocos-discovery-consumer-sample</artifactId> <version>0.0.1-SNAPSHOT</version> <name>nocos-discovery-consumer-sample</name> <description>Demo project for Spring Boot</description><properties> <java.version>1.8</java.version> <spring-cloud-alibaba.version>2021.0.4.0</spring-cloud-alibaba.version> <spring-cloud.version>2021.0.4</spring-cloud.version> </properties><dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>com.alibaba.cloud</groupId> <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter</artifactId> </dependency><dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-openfeign</artifactId> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-loadbalancer</artifactId> <version>3.0.1</version> </dependency> <dependency> <groupId>com.alibaba</groupId> <artifactId>fastjson</artifactId> <version>1.2.47</version> </dependency>
<dependency> <groupId>org.netbeans.external</groupId> <artifactId>org-apache-commons-httpclient</artifactId> <version>RELEASE126</version> </dependency>
</dependencies><dependencyManagement> <dependencies> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-dependencies</artifactId> <version>${spring-cloud.version}</version> <type>pom</type> <scope>import</scope> </dependency> <dependency> <groupId>com.alibaba.cloud</groupId> <artifactId>spring-cloud-alibaba-dependencies</artifactId> <version>${spring-cloud-alibaba.version}</version> <type>pom</type> <scope>import</scope> </dependency> </dependencies> </dependencyManagement><build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-compiler-plugin</artifactId> <version>3.8.1</version> <configuration> <source>1.8</source> <target>1.8</target> <encoding>UTF-8</encoding> </configuration> </plugin> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> </plugin> </plugins> </build></project>
5.application.properties的设置同前面的文章里介绍的设置一样,代码如下所示:
spring.application.name=nocos-discovery-consumer-sample
spring.cloud.nacos.discovery.username=nacos
spring.cloud.nacos.discovery.password=nacos
spring.cloud.nacos.discovery.server-addr=localhost:8848
spring.cloud.nacos.discovery.namespace=public
spring.main.allow-circular-references=true
server.port=9091
6.新建一个名为WeatherService的接口,代码如下:
importorg.springframework.cloud.openfeign.FeignClient;importorg.springframework.web.bind.annotation.GetMapping;importorg.springframework.cloud.loadbalancer.annotation.LoadBalancerClient;
@FeignClient("weatherforecast")
@LoadBalancerClient("weatherforecast")public interfaceWeatherService {
@GetMapping("/Weatherforecast")publicString getWeather();
}
7.新建一个RestTemplateController,代码如下:
importorg.springframework.web.bind.annotation.GetMapping;importorg.springframework.web.bind.annotation.PathVariable;importorg.springframework.web.bind.annotation.RestController;importorg.springframework.web.client.RestTemplate;
importcom.alibaba.fastjson.JSONObject;
importorg.springframework.context.annotation.Bean;importorg.apache.commons.httpclient.methods.GetMethod;//import org.apache.http.client.HttpClient; importorg.apache.commons.httpclient.HttpClient;importorg.springframework.beans.factory.annotation.Autowired;importorg.springframework.cloud.client.ServiceInstance;importorg.springframework.cloud.client.discovery.DiscoveryClient;importorg.springframework.cloud.client.loadbalancer.LoadBalanced;import java.io.*;
@RestControllerpublic classRestTemplateController {
//@LoadBalanced @AutowiredpublicRestTemplate resttemplate;//@LoadBalanced @BeanpublicRestTemplate restTemplate() {return newRestTemplate();
}
@AutowiredprivateEchoService echoService;
@AutowiredprivateWeatherService weatherService;
@Autowired DiscoveryClient discoveryClient;//resttemplate test @GetMapping("/call/echo")publicString callEcho() {
System.out.println("callEcho");
ServiceInstance serviceInstance=discoveryClient.getInstances("weatherforecast").get(0);
System.out.println("Host is: "+serviceInstance.getHost()+" ,port is: "+serviceInstance.getPort());
String urlString=serviceInstance.getHost()+":"+serviceInstance.getPort()+"/weatherforecast";
urlString="http://"+urlString;//RestTemplate test return resttemplate.getForObject(urlString, String.class);
}//openFeign test @GetMapping("/getWeather")publicString getWeather() {returnweatherService.getWeather();
}
}
其中要注意的几点:
1) ServiceInstanceserviceInstance=discoveryClient.getInstances(
"weatherforecast").
get(
0);是一句关键的代码,用于获取weatherforecast服务的实例。
2)callEcho()是调用RestTemplage访问netcore服务
3)getWeather是调用openFeiign访问netcore服务
8.启动类代码如下:
importorg.springframework.boot.SpringApplication;importorg.springframework.boot.autoconfigure.SpringBootApplication;
importorg.springframework.cloud.client.discovery.EnableDiscoveryClient;importorg.springframework.cloud.openfeign.EnableFeignClients;
@SpringBootApplication
@EnableDiscoveryClient
@EnableFeignClientspublic classNocosDiscoveryConsumerSampleApplication {
public static voidmain(String[] args) {
SpringApplication.run(NocosDiscoveryConsumerSampleApplication.class, args);
}
}
9.运行,访问http://192.168.1.110:5000/weatherforecast和http://localhost:9091/getWeather: