欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Eureka源碼閱讀解析Server服務(wù)端啟動(dòng)流程實(shí)例

 更新時(shí)間:2022年10月15日 12:49:39   作者:hsfxuebao  
這篇文章主要為大家介紹了Eureka源碼閱讀解析Server服務(wù)端啟動(dòng)流程實(shí)例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪

環(huán)境

本文主要看看spring cloud是怎樣自動(dòng)裝配eureka server 并啟動(dòng)eureka server的并解析其關(guān)鍵源碼。首先我們會(huì)配置啟動(dòng)一個(gè)spring cloud eureka server 服務(wù),接著看看是spring cloud怎樣自動(dòng)裝配eureka的,并看看一些核心組件的創(chuàng)建源碼,最后解析下eureka server 啟動(dòng)初始化流程,看看都干了些啥東西

1.spring cloud整合eureka server demo

1.1 新建spring boot項(xiàng)目

pom.xml文件添加

用來(lái)規(guī)范spring cloud 的版本:

<dependencyManagement>
    <!--引入springcloud依賴的-->
    <dependencies>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-dependencies</artifactId>
            <version>2020.0.2E</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
    </dependencies>
</dependencyManagement>

添加用到的依賴:

<dependencies>
    <!--web依賴-->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-actuator</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-commons</artifactId>
    </dependency>
    <!--unit test-->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
    </dependency>
    <!--spring cloud eureka server 依賴-->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
    </dependency>
</dependencies>

配置文件

eureka:
  instance:
    hostname: localhost
  client:
    service-url:   #  eureka server 的地址, 咱們單實(shí)例模式就寫(xiě)自己好了
      defaultZone:  http://localhost:7000/eureka
    register-with-eureka: false  # 不向eureka server 注冊(cè)自己
    fetch-registry: false  # 不向eureka server 獲取服務(wù)列表

1.2 啟動(dòng)類

@SpringBootApplication
@EnableEurekaServer
public class EurekaServer {
    public static void main(String[] args) {
        SpringApplication.run(EurekaServer.class, args);
    }
}

添加@EnableEurekaServer注解,表示它是個(gè)eureka server。

1.3 啟動(dòng)

訪問(wèn)地址:http://localhost:7000/

注意:由于是源碼解析的文章,更詳細(xì)的配置可以查看github.com/hsfxuebao/s…

2. spring cloud自動(dòng)裝配eureka server源碼解析

2.1 @EnableEurekaServer注解

上一節(jié)配置eureka server的時(shí)候我們?cè)谂渲妙惿霞恿藗€(gè)@EnableEurekaServer注解,表示啟動(dòng)一個(gè)eureka server 。 我們看看這個(gè)注解

@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Import(EurekaServerMarkerConfiguration.class)
public @interface EnableEurekaServer {
}

上面有個(gè)@Import(EurekaServerMarkerConfiguration.class) 注解導(dǎo)入了EurekaServerMarkerConfiguration配置類,我們看下配置類:

@Configuration
public class EurekaServerMarkerConfiguration {
	@Bean
	public Marker eurekaServerMarkerBean() {
		return new Marker();
	}
	class Marker {
	}
}

就是創(chuàng)建了一個(gè)EurekaServerMarkerConfiguration.Marker 對(duì)象,交給spring保管,一看就是個(gè)標(biāo)記,標(biāo)識(shí),僅僅是個(gè)標(biāo)識(shí)。

2.2 EurekaServerAutoConfiguration

2.2.1 查找starter 自動(dòng)裝配類的技巧

spring boot的starter基本都會(huì)自動(dòng)裝配類,也就是AutoConfiguration 結(jié)尾的類,如果我們找不到某個(gè)starter的自動(dòng)裝配類是那個(gè),可以去starter對(duì)應(yīng)jar 包里面META-INF 文件夾下面找spring.factories (這是spring spi 配置文件)文件。比如說(shuō)我可以在spring-cloud-netflix-eureka-server 這個(gè)項(xiàng)目下找到META-INF 文件夾下面找spring.factories文件。

文件內(nèi)容就是上圖里面的,可以看到自動(dòng)裝配類就是EurekaServerAutoConfiguration

2.2.2 EurekaServerAutoConfiguration源碼解析

首先,看看 EurekaServerAutoConfiguration 自動(dòng)配置類里面都干了啥。

@Configuration
@Import(EurekaServerInitializerConfiguration.class)
@ConditionalOnBean(EurekaServerMarkerConfiguration.Marker.class)
@EnableConfigurationProperties({ EurekaDashboardProperties.class,
		InstanceRegistryProperties.class })
@PropertySource("classpath:/eureka/server.properties")
public class EurekaServerAutoConfiguration extends WebMvcConfigurerAdapter{}

先看看類上面聲明的這一堆注解:

  • @Import(EurekaServerInitializerConfiguration.class) : 導(dǎo)入(裝配)配置類EurekaServerInitializerConfiguration,這個(gè)我們后面看下,屬于初始化流程。
  • @ConditionalOnBean(EurekaServerMarkerConfiguration.Marker.class) 就是是否存在EurekaServerMarkerConfiguration.Marker 類的bean實(shí)例,這個(gè)肯定存在的,我們?cè)?code>@EnableEurekaServer 注解中就創(chuàng)建了這么一個(gè)bean 交給spring 管理了。存在就會(huì)往下走,不存在就拉倒了,不會(huì)再加載配置類里面別的東西了,也就是不會(huì)自動(dòng)啟動(dòng)eureka server了。
  •  @EnableConfigurationProperties({ EurekaDashboardProperties.class, InstanceRegistryProperties.class }) 這個(gè)就是裝配這兩個(gè)配置類,一個(gè)是關(guān)于Dashboard 的,一個(gè)是關(guān)于instance 的配置,也就是eureka server的配置, 就是將我們寫(xiě)在application.yml配置文件中關(guān)于eureka 的配置set到這里面的屬性中。
  • @PropertySource(“classpath:/eureka/server.properties”) 加載/eureka/server.properties 配置文件,這個(gè)沒(méi)啥意思。

然后,看看里面成員有哪些。

@Autowired
private ApplicationInfoManager applicationInfoManager;
@Autowired
private EurekaServerConfig eurekaServerConfig;
@Autowired
private EurekaClientConfig eurekaClientConfig;
@Autowired
private EurekaClient eurekaClient;
@Autowired
private InstanceRegistryProperties instanceRegistryProperties;

ApplicationInfoManager / EurekaClientConfig / EurekaClient 這幾個(gè)bean 一看就是eureka client 里面的,我們這里是eureka server ,為啥能夠注入進(jìn)來(lái)呢?

  • 原因是 eureka server 的starter 里面依賴了eureka client starter,eureka client starter自動(dòng)裝配的這些實(shí)例bean 。有些小伙伴可能會(huì)有疑問(wèn),我啟用(自動(dòng)裝配)eureka client,不需要在配置類上面添加@EnableEurekaClient注解嘛。其實(shí)從spring cloud netflix 1.4版本往后主要引入了這個(gè) eureka client starter 依賴,就會(huì)自動(dòng)裝配,不需要添加@EnableEurekaClient 注解也是可以的。

接著,看看創(chuàng)建了哪些核心組件

dashboard 的controller

@Bean
@ConditionalOnProperty(prefix = "eureka.dashboard", name = "enabled", matchIfMissing = true)
public EurekaController eurekaController() {
return new EurekaController(this.applicationInfoManager);
}

注冊(cè)表創(chuàng)建

@Bean
public PeerAwareInstanceRegistry peerAwareInstanceRegistry(
                ServerCodecs serverCodecs) {
        this.eurekaClient.getApplications(); // force initialization
        return new InstanceRegistry(this.eurekaServerConfig, this.eurekaClientConfig,
                        serverCodecs, this.eurekaClient,
                        this.instanceRegistryProperties.getExpectedNumberOfClientsSendingRenews(),
                        this.instanceRegistryProperties.getDefaultOpenForTrafficCount());
}

注冊(cè)表,就是存放我們注冊(cè)的實(shí)例信息的,這個(gè)是個(gè)非常核心的組件。這里直接創(chuàng)建了一個(gè)InstanceRegistry 對(duì)象,這個(gè)InstanceRegistry繼承eureka server 里面PeerAwareInstanceRegistryImpl 類。

集群節(jié)點(diǎn)信息類對(duì)象

@Bean
@ConditionalOnMissingBean
public PeerEurekaNodes peerEurekaNodes(PeerAwareInstanceRegistry registry,
                ServerCodecs serverCodecs) {
        return new RefreshablePeerEurekaNodes(registry, this.eurekaServerConfig,
                        this.eurekaClientConfig, serverCodecs, this.applicationInfoManager);
}

PeerEurekaNodes 這個(gè)類,從名字上也能看出來(lái)是集群節(jié)點(diǎn)的類,而且是Nodes ,表示多個(gè)節(jié)點(diǎn),其實(shí)里面就是封裝eureka server 集群的節(jié)點(diǎn)們。這里是創(chuàng)建RefreshablePeerEurekaNodes 對(duì)象,RefreshablePeerEurekaNodes繼承PeerEurekaNodes 類,實(shí)現(xiàn)spring 的ApplicationListener 事件監(jiān)聽(tīng)接口,自然而然的RefreshablePeerEurekaNodes類具有了刷新集群節(jié)點(diǎn)信息功能(能力)。

EurekaServerContext

@Bean
public EurekaServerContext eurekaServerContext(ServerCodecs serverCodecs,
                PeerAwareInstanceRegistry registry, PeerEurekaNodes peerEurekaNodes) {
        return new DefaultEurekaServerContext(this.eurekaServerConfig, serverCodecs,
                        registry, peerEurekaNodes, this.applicationInfoManager);
}

EurekaServerContext 從字面上是eureka server 上下文,其實(shí)就是eureka server 啟動(dòng)的時(shí)候會(huì)初始化PeerEurekaNodesPeerAwareInstanceRegistry 注冊(cè)表,銷毀的是否停止這2個(gè)組件

EurekaServerBootstrap

@Bean
public EurekaServerBootstrap eurekaServerBootstrap(PeerAwareInstanceRegistry registry,
                EurekaServerContext serverContext) {
        return new EurekaServerBootstrap(this.applicationInfoManager,
                        this.eurekaClientConfig, this.eurekaServerConfig, registry,
                        serverContext);
}

一般叫Bootstrap 的類都是那種掌管項(xiàng)目啟動(dòng)與停止的,EurekaServerBootstrap 也不例外,它里面就有contextInitialized 項(xiàng)目啟動(dòng)與contextDestroyed項(xiàng)目停止/銷毀的方法。

jersey框架 關(guān)于jersey框架的東西,eureka server 對(duì)外暴露rest ful接口,使用的框架就是jersey(這玩意國(guó)內(nèi)很少用),作用/定位就跟我們常用的springmvc 框架差不多。

3. eureka server 初始化源碼解析

3.1 EurekaServerInitializerConfiguration

第2小節(jié)介紹 spring cloud eureka server 啟動(dòng)的時(shí)候自動(dòng)裝配的一些組件,本小節(jié)就看下eureka server的初始化流程。

在自動(dòng)裝配類EurekaServerAutoConfiguration 類上面聲明了@Import(EurekaServerInitializerConfiguration.class) ,我們介紹說(shuō)是導(dǎo)入(加載)EurekaServerInitializerConfiguration 這個(gè)配置,一看這個(gè)類名字就是eureka server 初始化用的。

@Configuration
public class EurekaServerInitializerConfiguration
		implements ServletContextAware, SmartLifecycle, Ordered {
}

@Configuration是個(gè)配置類,實(shí)現(xiàn)ServletContextAware,SmartLifecycle,Ordered 接口:

  • ServletContextAware 作用是自動(dòng)注入ServletContext 實(shí)例。
  • SmartLifecycle接口 屬于spring 聲明周期的,start 方法執(zhí)行時(shí)機(jī)是,當(dāng)spring 的bean都實(shí)例化,初始化完事后,會(huì)調(diào)用SmartLifecycle 的start方法,isAutoStartup 方法返回的true 或者false 決定要不要執(zhí)行start方法,這里isAutoStartup方法返回的true。
  • stop 方法就是項(xiàng)目停止,容器銷毀的時(shí)候會(huì)調(diào)用。

先來(lái)看下start 方法干了啥

@Override
public void start() {
	new Thread(new Runnable() {
		@Override
		public void run() {
			try {
				//TODO: is this class even needed now?
				eurekaServerBootstrap.contextInitialized(EurekaServerInitializerConfiguration.this.servletContext);
				log.info("Started Eureka Server");
				publish(new EurekaRegistryAvailableEvent(getEurekaServerConfig()));
				EurekaServerInitializerConfiguration.this.running = true;
				publish(new EurekaServerStartedEvent(getEurekaServerConfig()));
			}
			catch (Exception ex) {
				// Help!
				log.error("Could not initialize Eureka servlet context", ex);
			}
		}
	}).start();
}

創(chuàng)建了一個(gè)線程,先是執(zhí)行eurekaServerBootstrapcontextInitialized 初始化方法。接著就是發(fā)布 EurekaRegistryAvailableEvent 事件,設(shè)置running 為true ,最后就是發(fā)布EurekaServerStartedEvent 事件。 這里我們只關(guān)心eurekaServerBootstrap的contextInitialized 方法。

public void contextInitialized(ServletContext context) {
	initEurekaEnvironment();
	initEurekaServerContext();
	context.setAttribute(EurekaServerContext.class.getName(), this.serverContext);
}

初始化eureka environment, 接著初始化context,最后是將context塞到 ServletContext的屬性中。 initEurekaEnvironment這個(gè)我們就不看了。主要看下initEurekaServerContext 方法:

if (isAws(this.applicationInfoManager.getInfo())) {
	this.awsBinder = new AwsBinderDelegate(this.eurekaServerConfig,
			this.eurekaClientConfig, this.registry, this.applicationInfoManager);
	this.awsBinder.start();
}
EurekaServerContextHolder.initialize(this.serverContext);
log.info("Initialized server context");
// Copy registry from neighboring eureka node
int registryCount = this.registry.syncUp();
this.registry.openForTraffic(this.applicationInfoManager, registryCount);
// Register all monitoring statistics.
EurekaMonitors.registerAllStats();

isAws 是亞馬遜云環(huán)境的時(shí)候執(zhí)行if里面的那一堆,這個(gè)不看了。

EurekaServerContextHolder.initialize(this.serverContext);這行代碼沒(méi)干啥。

int registryCount = this.registry.syncUp();
this.registry.openForTraffic(this.applicationInfoManager, registryCount);

registry.syncUp()這個(gè)就是去集群中的其他節(jié)點(diǎn)拉取注冊(cè)表。下篇文章分析 registry.openForTraffic()這個(gè)是Server端定時(shí)清理過(guò)期的Client。以后在詳細(xì)分析。

3.2 DefaultEurekaServerContext

我們?cè)诮榻B自動(dòng)裝配類EurekaServerAutoConfiguration 裝配組件的時(shí)候,介紹過(guò)EurekaServerContext ,說(shuō)他字面上是eureka server 上下文,其實(shí)就是eureka server 啟動(dòng)的時(shí)候會(huì)初始化PeerEurekaNodes 與PeerAwareInstanceRegistry 注冊(cè)表,銷毀的是否停止這2個(gè)組件 我們來(lái)看下 @PostConstruct 注解修飾的initialize 方法

@PostConstruct
public void initialize() {
    this.peerEurekaNodes.start();
    this.registry.init(this.peerEurekaNodes);
}

干了2件事,啟動(dòng)peerEurekaNodes ,初始化注冊(cè)表。 peerEurekaNodes#start:

public void start() {
     updatePeerEurekaNodes(resolvePeerUrls());
     Runnable peersUpdateTask = new Runnable() {
         @Override
         public void run() {
             updatePeerEurekaNodes(resolvePeerUrls());
         }
     };
     taskExecutor.scheduleWithFixedDelay(
             peersUpdateTask,
             serverConfig.getPeerEurekaNodesUpdateIntervalMs(),
             serverConfig.getPeerEurekaNodesUpdateIntervalMs(),
             TimeUnit.MILLISECONDS
     );
}

先是更新集群節(jié)點(diǎn)信息,就是創(chuàng)建節(jié)點(diǎn)對(duì)象。

接著就是創(chuàng)建一個(gè)定時(shí)任務(wù)更新,默認(rèn)是10分鐘。

注冊(cè)表初始化:

@Override
public void init(PeerEurekaNodes peerEurekaNodes) throws Exception {
    this.numberOfReplicationsLastMin.start();
    this.peerEurekaNodes = peerEurekaNodes;
    initializedResponseCache();
    scheduleRenewalThresholdUpdateTask();
    initRemoteRegionRegistry();
}
  • numberOfReplicationsLastMin 這是記錄續(xù)約次數(shù)的一個(gè)組件,用在服務(wù)剔除。
  • initializedResponseCache 初始化響應(yīng)cache ,這個(gè)其實(shí)就是 服務(wù)發(fā)現(xiàn)的時(shí)候三級(jí)緩存。

參考

eureka-0.10.11源碼(注釋)

springcloud-source-study學(xué)習(xí)github地址

以上就是Eureka源碼閱讀解析Server服務(wù)端啟動(dòng)流程實(shí)例的詳細(xì)內(nèi)容,更多關(guān)于Eureka Server服務(wù)端啟動(dòng)流程的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!

相關(guān)文章

  • springboot2.x實(shí)現(xiàn)oauth2授權(quán)碼登陸的方法

    springboot2.x實(shí)現(xiàn)oauth2授權(quán)碼登陸的方法

    這篇文章主要介紹了springboot2.x實(shí)現(xiàn)oauth2授權(quán)碼登陸的方法,本文給大家介紹的非常詳細(xì),具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2019-08-08
  • MAC下基于maven使用IDEA走讀TestNG源碼解析

    MAC下基于maven使用IDEA走讀TestNG源碼解析

    這篇文章主要介紹了MAC下基于maven使用IDEA走讀TestNG源碼,本文給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2021-06-06
  • Java排序?qū)崿F(xiàn)的心得分享

    Java排序?qū)崿F(xiàn)的心得分享

    這篇文章主要介紹了Java排序?qū)崿F(xiàn)的心得,有需要的朋友可以參考一下
    2014-01-01
  • 最新評(píng)論