本文分享自華為云社區(qū)《Java Chassis 3技術(shù)解密:與Spring Cloud的互操作》,作者: liubao68。
Java Chassis 3一個(gè)很重要的設(shè)計(jì)原則:利用架構(gòu)的韌性設(shè)計(jì)來解決兼容性問題。
比如通過引入微服務(wù)網(wǎng)關(guān),來解決不同語(yǔ)言、不同框架、遺留系統(tǒng)之間的互操作問題。 本文在這個(gè)架構(gòu)原則基礎(chǔ)上,討論一個(gè)更加細(xì)粒度的互操作問題,并借此解密Java Chassis3在運(yùn)行時(shí)設(shè)計(jì)依賴上的技術(shù)細(xì)節(jié)。
首先,我們描述一個(gè)互操作的場(chǎng)景和假設(shè)。
- Spring Cloud和Java Chassis應(yīng)用同時(shí)注冊(cè)到注冊(cè)中心。引入了Spring Cloud Gateway作為網(wǎng)關(guān),網(wǎng)關(guān)也注冊(cè)到注冊(cè)中心。
- Spring Cloud微服務(wù)和Java Chassis微服務(wù)相互調(diào)用。它們彼此作為消費(fèi)者的時(shí)候,不需要感知對(duì)方是不同的框架,做到透明調(diào)用。
從技術(shù)原理上梳理下上述互操作需要滿足的條件:
- Spring Cloud和Java Chassis需要有相互認(rèn)識(shí)的注冊(cè)信息。核心包括:應(yīng)用名稱、服務(wù)名稱、地址信息和格式等。 需要的共同注冊(cè)中心越少,越容易對(duì)注冊(cè)中心和客戶端進(jìn)行選型。 在本例子中,我們選擇?
Service Center
?或者?Nacos
?作為注冊(cè)中心,并選擇Spring Cloud Huawei實(shí)現(xiàn)Spring Cloud注冊(cè)。 - Spring Cloud訪問Java Chassis,只需要一個(gè)地址信息,依賴較少。 Java Chassis訪問Spring Cloud,需要知道Spring Cloud應(yīng)用提供的契約信息。
Java Chassis區(qū)別于Spring Cloud的REST調(diào)用的部分,就是契約依賴。 Spring Cloud通過FeignClient來聲明客戶端契約,客戶端都需要在FeignClient中重復(fù)書寫REST標(biāo)簽;Java Chassis有兩種模式發(fā)現(xiàn)契約:從注冊(cè)中心發(fā)現(xiàn)和從Provider實(shí)例發(fā)現(xiàn)。 Java Chassis3默認(rèn)采用從Provider實(shí)例發(fā)現(xiàn), Java Chassis2采用從注冊(cè)中心發(fā)現(xiàn)。 從Provider發(fā)現(xiàn)的好處是可以降低對(duì)于注冊(cè)中心元數(shù)據(jù)管理能力的要求,本例既可以采用?Service Center
?作為注冊(cè)中心,也可以選擇?Nacos
?作為注冊(cè)中心。
從Provider發(fā)現(xiàn),要求Provider實(shí)現(xiàn)如下接口:
/** * Java Chassis internal management apis. */ @Path("/scb/management") public interface ManagementEndpoint { String NAME = "scb-management"; /** * Health of this instance. If the instanceId match this instance, and this service is ready * to service return true. Otherwise, return false. * * This api is for internal instance status usage. Load balancer will call this api to check if * the target instance is alive. */ @GET @Path("/health") boolean health(@QueryParam("instanceId") String instanceId, @QueryParam("registryName") String registryName); /** * Schemas of this instance. * * This api is for internal schema loading usage. */ @POST @Path("/schema/contents") Map<String, String> schemaContents(); }
它包含一個(gè)健康檢查接口和一個(gè)查詢契約的接口。 當(dāng)Spring Cloud應(yīng)用實(shí)現(xiàn)上述接口以后,它就具備了Java Chassis微服務(wù)需要的基礎(chǔ)特征,這樣Java Chassis就可以像訪問本框架的微服務(wù)一樣訪問Spring Cloud框架開發(fā)的微服務(wù)應(yīng)用。 為了簡(jiǎn)化,在Spring Cloud簡(jiǎn)單實(shí)現(xiàn)了該接口,該實(shí)現(xiàn)接口從?export
?目錄加載契約信息,只需要將Spring Cloud需要對(duì)外暴露的 REST 接口的符合 Open API 3.0規(guī)范的契約文件放到這個(gè)目錄下面 。
@RestController @RequestMapping(("/scb/management")) public class JavaChassisManagementEndpoint { private static final Logger LOGGER = LoggerFactory.getLogger(JavaChassisManagementEndpoint.class); @Autowired private Registration registration; @GetMapping(path = "/health") public boolean health(@RequestParam("instanceId") String instanceId, @RequestParam("registryName") String registryName) { return "sc-registry".equals(registryName) && registration.getInstanceId().equals(instanceId); } @PostMapping(path = "/schema/contents") public Map<String, String> schemaContents() { try { List<URI> resourceUris = ResourceUtil.findResourcesBySuffix("export", ".yaml"); Map<String, String> result = new HashMap<>(resourceUris.size()); for (URI uri : resourceUris) { String path = uri.toURL().getPath(); String[] segments = path.split("/"); if (segments.length < 2 || !"export".equals(segments[segments.length - 2])) { continue; } result.put(segments[segments.length - 1].substring(0, segments[segments.length - 1].indexOf(".yaml")), IOUtils.toString(uri, StandardCharsets.UTF_8)); } return result; } catch (IOException | URISyntaxException e) { LOGGER.error("Load schema ids failed from microservices. {}.", e.getMessage()); return Collections.emptyMap(); } } }
Java Chassis與Spring Cloud互操作的例子放到了ServiceComb Samples?, 這個(gè)例子也提供了使用 Nacos 作為注冊(cè)中心和配置中心的實(shí)現(xiàn), 只需要將 Profile 設(shè)置為 Nacos 即可。
客戶故事:在架構(gòu)選型變化的時(shí)候,解決功能遷移和兼容性問題是最大的挑戰(zhàn)。一些客戶將Spring Cloud應(yīng)用改造為Java Chassis的過程中,發(fā)現(xiàn)一些功能不支持,比如SseEmitter、WebSocket等。 如果選擇支持這些能力,Java Chassis需要實(shí)現(xiàn)很多Servlet能力,這些能力規(guī)劃會(huì)和微服務(wù)技術(shù)架構(gòu)存在沖突。 對(duì)于這些場(chǎng)景,我們選擇通過架構(gòu)韌性來保留這些功能,比如將提供SseEmitter、WebSocket功能的獨(dú)立出微服務(wù),采用Spring Boot開發(fā),這些應(yīng)用可以通過調(diào)用Java Chassis微服務(wù)的REST接口來實(shí)現(xiàn)其特殊功能。通過這種架構(gòu)韌性的理念,降低了技術(shù)持續(xù)演進(jìn)的包袱,為敏捷迭代,持續(xù)創(chuàng)新奠定了方向,減少了兼容性問題的爭(zhēng)論。
?文章來源地址http://www.zghlxwxcb.cn/news/detail-846447.html
點(diǎn)擊關(guān)注,第一時(shí)間了解華為云新鮮技術(shù)~文章來源:http://www.zghlxwxcb.cn/news/detail-846447.html
?
到了這里,關(guān)于詳解Java Chassis 3與Spring Cloud的互操作的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!