高可用eureka服務發現實例

轉載請註明出處 http://www.paraller.com
原文排版地址 點擊跳轉html

spring:
application:java

name: eureka-server-clustered3

profiles: peer3
server:
port: 9763
host: serverA
eureka:
instance:mysql

hostname: eureka-peer3
preferIpAddress: true
instance-id: ${spring.cloud.client.ipAddress}:${server.port}:${spring.application.name}

client:git

registerWithEureka: true
fetchRegistry: true
serviceUrl:
  defaultZone: http://${server.host}:9761/eureka/,http://${server.host}:9762/eureka/
##### 配置2: application.properties

application-peer1.properties

eureka.client.fetchRegistry=true
eureka.client.registerWithEureka=true
eureka.client.serviceUrl.defaultZone=http://serverA:9762/eureka/,http://serverA:9763/eureka/
eureka.instance.hostname=serverA
eureka.instance.metadataMap.instanceId=${spring.application.name}\:${spring.application.instance_id:${random.value}}
eureka.server.waitTimeInMsWhenSyncEmpty=0
server.port=9761
spring.application.name=server_peer1redis

application-peer2.properties

eureka.client.fetchRegistry=true
eureka.client.registerWithEureka=true
eureka.client.serviceUrl.defaultZone=http://serverA:9761/eureka/,http://serverA:9763/eureka/
eureka.instance.hostname=serverA
eureka.server.waitTimeInMsWhenSyncEmpty=0
server.port=9762
eureka.instance.metadataMap.instanceId=${spring.application.name}\:${spring.application.instance_id:${random.value}}
spring.application.name=server_peer2spring

application-peer3.properties

eureka.client.fetchRegistry=true
eureka.client.registerWithEureka=true
eureka.client.serviceUrl.defaultZone=http://serverA:9761/eureka/,http://serverA:9762/eureka/
eureka.instance.hostname=serverA
eureka.server.waitTimeInMsWhenSyncEmpty=0
server.port=9763
eureka.instance.metadataMap.instanceId=${spring.application.name}\:${spring.application.instance_id:${random.value}}
spring.application.name=server_peer3sql

##### 本地跑測試的時候,須要編輯 etc/hosts

127.0.0.1 serverAdocker

##### Dockerfile 文件

FROM java:7
VOLUME /tmp
ADD eureka-0.0.1-SNAPSHOT.jar /app.jar
RUN bash -c 'touch /app.jar'
EXPOSE 9762
ENTRYPOINT ["java","-Djava.security.egd=file:/dev/./urandom","-jar","/app.jar"]apache

##### pom.xml

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"vim

xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>

<groupId>org.demo</groupId>
<artifactId>eureka</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>

<name>Eureka Server</name>
<description>Eureka Server demo project</description>

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>1.4.3.RELEASE</version>
    <relativePath />
</parent>
<properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <!-- springBoot 程序的主入口 -->
    <start-class>eurekademo.EurekaApplication</start-class> 
    <java.version>1.7</java.version>
    <docker.registry>docker.umiit.cn:5043</docker.registry>

</properties>

<profiles>
    <profile>
        <id>dev</id>
        <properties>
            <env>dev</env>
        </properties>
        <activation>
            <activeByDefault>true</activeByDefault>
        </activation>
    </profile>
    <profile>
        <id>peer1</id>
        <properties>
            <env>peer1</env>
            <docker>peer1</docker>
        </properties>
    </profile>
    <profile>
        <id>peer2</id>
        <properties>
            <env>peer2</env>
            <docker>peer2</docker>
        </properties>
    </profile>
    <profile>
        <id>peer3</id>
        <properties>
            <env>peer3</env>
            <docker>peer3</docker>
        </properties>
    </profile>
</profiles>

<dependencies>
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-eureka-server</artifactId>
        <version>1.3.0.RELEASE</version>
    </dependency>
    <!-- <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-config</artifactId> 
        </dependency> -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>
</dependencies>

<dependencyManagement>
    <dependencies>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-dependencies</artifactId>
            <version>Camden.SR6</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
    </dependencies>
</dependencyManagement>
<build>
    <plugins>
        <plugin>
            <groupId>com.spotify</groupId>
            <artifactId>docker-maven-plugin</artifactId>
            <version>0.2.11</version>
            <configuration>
                <pushImage>true</pushImage>
                <imageName>
                    ${docker.registry}/v3/${project.artifactId}:${docker}
                </imageName>

                <dockerDirectory>src/main/resources_${env}/docker</dockerDirectory>
                <resources>
                    <resource>
                        <targetPath>/</targetPath>
                        <directory>${project.build.directory}</directory>
                        <include>${project.build.finalName}.jar</include>
                    </resource>
                </resources>
            </configuration>
        </plugin>
        <plugin>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-maven-plugin</artifactId>
            <!-- defined in spring-cloud-starter-parent pom (as documentation hint), 
                but needs to be repeated here -->
            <configuration>
                <requiresUnpack>
                    <dependency>
                        <groupId>com.netflix.eureka</groupId>
                        <artifactId>eureka-core</artifactId>
                    </dependency>
                    <dependency>
                        <groupId>com.netflix.eureka</groupId>
                        <artifactId>eureka-client</artifactId>
                    </dependency>
                </requiresUnpack>
            </configuration>
        </plugin>
        <plugin>
            <groupId>pl.project13.maven</groupId>
            <artifactId>git-commit-id-plugin</artifactId>
            <configuration>
                <failOnNoGitDirectory>false</failOnNoGitDirectory>
            </configuration>
        </plugin>
        <plugin>
            <!--skip deploy (this is just a test module) -->
            <artifactId>maven-deploy-plugin</artifactId>
            <configuration>
                <skip>true</skip>
            </configuration>
        </plugin>
        <plugin>
            <groupId>org.codehaus.mojo</groupId>
            <artifactId>build-helper-maven-plugin</artifactId>
            <executions>
                <execution>
                    <id>add-resource</id>
                    <phase>initialize</phase>
                    <goals>
                        <goal>add-resource</goal>
                    </goals>
                    <configuration>
                        <resources>
                            <resource>
                                <directory>src/main/resources_${env}</directory>
                            </resource>
                        </resources>
                    </configuration>
                </execution>
            </executions>
        </plugin>
    </plugins>
</build>

<repositories>
    <repository>
        <id>spring-snapshots</id>
        <name>Spring Snapshots</name>
        <url>https://repo.spring.io/libs-snapshot-local</url>
        <snapshots>
            <enabled>true</enabled>
        </snapshots>
    </repository>
    <repository>
        <id>spring-milestones</id>
        <name>Spring Milestones</name>
        <url>https://repo.spring.io/libs-milestone-local</url>
        <snapshots>
            <enabled>false</enabled>
        </snapshots>
    </repository>
    <repository>
        <id>spring-releases</id>
        <name>Spring Releases</name>
        <url>https://repo.spring.io/libs-release-local</url>
        <snapshots>
            <enabled>false</enabled>
        </snapshots>
    </repository>
</repositories>
<pluginRepositories>
    <pluginRepository>
        <id>spring-snapshots</id>
        <name>Spring Snapshots</name>
        <url>https://repo.spring.io/libs-snapshot-local</url>
        <snapshots>
            <enabled>true</enabled>
        </snapshots>
    </pluginRepository>
    <pluginRepository>
        <id>spring-milestones</id>
        <name>Spring Milestones</name>
        <url>https://repo.spring.io/libs-milestone-local</url>
        <snapshots>
            <enabled>false</enabled>
        </snapshots>
    </pluginRepository>
</pluginRepositories>

</project>

##### .gitlab-ci.yml

image: docker.umiit.cn:5043/maven_docker:latest

stages:

  • build

run_build_peer1:
stage: build
tags:

- docker

only:

- develop

script:

- mvn clean package docker:build -Ppeer1

run_build_peer2:
stage: build
tags:

- docker

only:

- develop

script:

- mvn clean package docker:build -Ppeer2

run_build_peer3:
stage: build
tags:

- docker

only:

- develop

script:

- mvn clean package docker:build -Ppeer3
##### docker-compose.yml

eureka_1:
image: docker.umiit.cn:5043/v3/eureka:peer1
volumes:

- /etc/localtime:/etc/localtime:ro
- /etc/timezone:/etc/timezone:ro
- /mnt/docker-data/logstash/eureka_1:/usr/local/tomcat/logs

environment:

spring.profiles.active: peer1

ports:

- "公網IP:9761:9761"

eureka_2:
image: docker.umiit.cn:5043/v3/eureka:peer2
volumes:

- /etc/localtime:/etc/localtime:ro
- /etc/timezone:/etc/timezone:ro
- /mnt/docker-data/logstash/eureka_2:/usr/local/tomcat/logs

environment:

spring.profiles.active: peer2

ports:

- "公網IP:9762:9762"

eureka_3:
image: docker.umiit.cn:5043/v3/eureka:peer3
volumes:

- /etc/localtime:/etc/localtime:ro
- /etc/timezone:/etc/timezone:ro
- /mnt/docker-data/logstash/eureka_2:/usr/local/tomcat/logs

environment:

spring.profiles.active: peer3

ports:

- "公網IP:9763:9763"
##### 項目結構

|-- src/main/resources_peer1
|-- src/main/resources_peer2
|-- src/main/resources_peer3

放置 Dockerfile & application.yml

##### 本地測試

mvn package

java -jar eureka-server-0.0.1-SNAPSHOT.jar --spring.profiles.active=peer1
java -jar eureka-server-0.0.1-SNAPSHOT.jar --spring.profiles.active=peer2
java -jar eureka-server-0.0.1-SNAPSHOT.jar --spring.profiles.active=peer3

### 客戶端配置

##### application.yml

server:
port: ${vcap.application.port:9099}

eureka:
instance:

preferIpAddress: true

client:

serviceUrl:
  defaultZone: http://${serverA}:9761/eureka/,http://${serverA}:9762/eureka/,http://${serverA}:9763/eureka/
registerWithEureka: true
fetchRegistry: true
##### docker-compose.yml

ticketservice:
image: docker.umiit.cn:5043/v3/ticket-service:prep
volumes:

- /etc/localtime:/etc/localtime:ro
- /etc/timezone:/etc/timezone:ro
- /mnt/docker-data/logstash/ticketservice:/logs

external_links:

- common_mysql_1:mysqlDb
- common_redis_1:redisDb
- common_mongo_1:mongoDb

environment:

serverA: localhost
JVM_ARGS: -Xmx1024m

ports:

- "0.0.0.0:9099:9099"

yeaservice:
image: docker.umiit.cn:5043/v3/yea-service:ipc
volumes:

- /etc/localtime:/etc/localtime:ro
- /etc/timezone:/etc/timezone:ro
- /mnt/docker-data/logstash/yeaservice:/logs

external_links:

- common_mysql_1:mysqlDb
- common_redis_1:redisDb
- common_mongo_1:mongoDb

environment:

serverA: localhost
JVM_ARGS: -Xmx1024m

ports:

- "0.0.0.0:8081:8081"

hystrix-dashboard:
image: kennedyoliveira/hystrix-dashboard
ports:

- "0.0.0.0:7979:7979"

environment:

JVM_ARGS: -Xmx512m
##### yeaservice - Application.java

@SpringBootApplication
@EnableEurekaClient
@EnableFeignClients
@EnableDiscoveryClient
@EnableCircuitBreaker
@EnableHystrixDashboard
@RibbonClient(name = "yea-ribbon", configuration = YeaRibbonConfiguration.class)
@ComponentScan(basePackages = { "com.**" })
public class Application {

public static void main(String[] args) {
    SpringApplication.run(Application.class, args);
}

}

##### yeaservice - 調用 ticketservice

@FeignClient(value = "ticket-service")
interface TicketClient {

}

這裏使用了Feign的框架演示。



### 查看結果

curl -i IP:9761/ # 在瀏覽器中輸入網址

## 官方知識點

### Authenticating with the Eureka Server

HTTP basic authentication will be automatically added to your eureka client if one of the eureka.client.serviceUrl.defaultZone URLs has credentials embedded in it (curl style, like http://user:password@localhost:8761/eureka). For more complex needs you can create a @Bean of type DiscoveryClientOptionalArgs and inject ClientFilter instances into it, all of which will be applied to the calls from the client to the server.

### Zones

但願在不一樣的Zone中配置你的客戶端,首先要確認你的Eureka servers 部署在不一樣的Zone中,而且互相鏈接了,接下來要告訴Server你的服務實例在哪裏,你能夠使用`metadataMap`屬性,例如像下面這樣配置:

##### Service 1 in Zone 1

eureka.instance.metadataMap.zone = zone1
eureka.client.preferSameZoneEureka = true

##### Service 1 in Zone 2

eureka.instance.metadataMap.zone = zone2
eureka.client.preferSameZoneEureka = true

NOTE
Because of a limitation in Eureka it isn’t possible to support per-server basic auth credentials, so only the first set that are found will be used.

### 單例模式

若是是單例模式的話,沒必要開啓下面的選項,由於心跳檢測會不斷的進行,會報錯鏈接不上。

eureka:
instance:

hostname: localhost

client:

registerWithEureka: false            ## this
fetchRegistry: false                ## this    
serviceUrl:
  defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/
## 參考連接

[如何實現微服務架構中的服務發現](http://www.jiagoushuo.com/article/1000415.html)

[Microservice Registration and Discovery with Spring Cloud and Netflix's Eureka](https://spring.io/blog/2015/01/20/microservice-registration-and-discovery-with-spring-cloud-and-netflix-s-eureka)

[Spring Cloud構建微服務架構(一)服務註冊與發現](http://blog.didispace.com/springcloud1/)

[Spring Cloud Netflix](http://cloud.spring.io/spring-cloud-static/spring-cloud-netflix/1.2.7.RELEASE/)



## QA 

**使用serverA 的域名配置,修改宿主機的  /etc/hosts ,不能集羣鏈接**

須要在docker容器中配置 /etc/hosts, 因此 vim Dockerfile

RUN echo '10.45.189.178 serverA' >> /etc/hosts

從新啓動,發現仍是無效,cat /etc/hosts 沒有寫進serverA 的映射,後面推測應該是容器的/etc/hosts是動態生成的,因此這個語句無效。
從環境變量開始入手
docker-compose.yml

environment:serverA: 內網IP

相關文章
相關標籤/搜索