├── .gitignore
├── .travis.yml
├── README.md
├── grpc-eureka-java-starter
├── META-INF
│ └── spring.factories
├── pom.xml
└── src
│ └── main
│ └── java
│ └── org
│ └── exampledriven
│ └── grpc
│ └── eureka
│ └── GrpcEurekaConfiguration.java
├── grpc-eureka-java
├── pom.xml
└── src
│ └── main
│ └── java
│ └── org
│ └── exampledriven
│ └── grpc
│ └── eureka
│ ├── EurekaNameResolver.java
│ └── EurekaNameResolverProvider.java
└── pom.xml
/.gitignore:
--------------------------------------------------------------------------------
1 | target
2 | *.iml
3 | .idea
--------------------------------------------------------------------------------
/.travis.yml:
--------------------------------------------------------------------------------
1 | language: java
2 | jdk: oraclejdk8
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | [](https://maven-badges.herokuapp.com/com.github.exampledriven/grpc-eureka-java/rsql-parser)
2 |
3 | [](https://travis-ci.org/ExampleDriven/grpc-eureka-java)
4 |
5 | # GRPC, Eureka integration in Java
6 |
7 | This project integrates GRPC with Eureka, the best way to understand how it works is to look at the [example code](https://github.com/ExampleDriven/spring-boot-grpc-example)
8 |
9 | ## Server setup
10 | The server does not need any special setup, it should just start GRPC the usual way and register itself to Eureka the usual way
11 |
12 | ## Client setup
13 |
14 | ### Using the Spring Boot Starter
15 |
16 | 1. Add the starter dependency to your project
17 | ```xml
18 |
19 | com.github.exampledriven
20 | grpc-eureka-java-starter
21 | version
22 |
23 | ```
24 |
25 |
26 | 2. Set the `grpc.eureka.service-id` property to the service id of your server
27 |
28 | 3. A default instance of ManagedChannel is auto created for you. You can use it like this
29 |
30 | ```Java
31 |
32 | @Autowired
33 | ManagedChannel managedChannel;
34 |
35 | @PostConstruct
36 | private void initializeClient() {
37 |
38 | bookServiceBlockingStub = BookServiceGrpc.newBlockingStub(managedChannel);
39 |
40 | }
41 |
42 | ```
43 |
44 | ## Without using Spring Boot Starter
45 |
46 | 1. Add the following dependency
47 |
48 | ```xml
49 |
50 | com.github.exampledriven
51 | grpc-eureka-java
52 | version
53 |
54 | ```
55 |
56 | 2. You have to manually create an instance of ManagedChannel like this
57 |
58 | ```Java
59 | return ManagedChannelBuilder
60 | .forTarget("eureka://" + eurekaServiceId)
61 | .nameResolverFactory(new EurekaNameResolverProvider(eurekaClientConfig, "grpc.port"))
62 | .loadBalancerFactory(RoundRobinLoadBalancerFactory.getInstance())
63 | .usePlaintext(true)
64 | .build();
65 | ```
--------------------------------------------------------------------------------
/grpc-eureka-java-starter/META-INF/spring.factories:
--------------------------------------------------------------------------------
1 | org.springframework.boot.autoconfigure.EnableAutoConfiguration=org.exampledriven.grpc.eureka.GrpcEurekaConfiguration
--------------------------------------------------------------------------------
/grpc-eureka-java-starter/pom.xml:
--------------------------------------------------------------------------------
1 |
3 | 4.0.0
4 |
5 |
6 | com.github.exampledriven
7 | grpc-eureka-java-parent
8 | 1.0.0-SNAPSHOT
9 |
10 |
11 | grpc-eureka-java-starter
12 | jar
13 |
14 | GRPC Eureka Java integration Starter
15 |
16 | https://github.com/ExampleDriven/
17 |
18 | Spring Boot Starter for Eureka integration with GRPC
19 |
20 |
21 | Exampledriven
22 | exampledriven.wordpress.com
23 |
24 |
25 |
26 | Apache License, Version 2.0
27 | http://www.apache.org/licenses/LICENSE-2.0
28 |
29 |
30 |
31 |
32 |
33 | szantop
34 | Peter Szanto
35 | Exampledriven
36 | exampledriven.wordpress.com
37 |
38 | Project lead
39 |
40 |
41 |
42 |
43 |
44 |
45 | UTF-8
46 | 1.8
47 | 1.8
48 | 0.15.0
49 |
50 |
51 |
52 |
53 |
54 | com.github.exampledriven
55 | grpc-eureka-java
56 | 1.0.0-SNAPSHOT
57 |
58 |
59 |
60 | org.springframework
61 | spring-context
62 | 4.3.3.RELEASE
63 | provided
64 |
65 |
66 |
67 | org.springframework.boot
68 | spring-boot-autoconfigure
69 | 1.4.1.RELEASE
70 | provided
71 |
72 |
73 |
74 | io.grpc
75 | grpc-stub
76 | provided
77 |
78 |
79 |
80 | com.netflix.eureka
81 | eureka-client
82 | provided
83 |
84 |
85 |
86 |
87 |
--------------------------------------------------------------------------------
/grpc-eureka-java-starter/src/main/java/org/exampledriven/grpc/eureka/GrpcEurekaConfiguration.java:
--------------------------------------------------------------------------------
1 | package org.exampledriven.grpc.eureka;
2 |
3 | import com.netflix.discovery.EurekaClientConfig;
4 | import io.grpc.ManagedChannel;
5 | import io.grpc.ManagedChannelBuilder;
6 | import io.grpc.util.RoundRobinLoadBalancerFactory;
7 | import org.springframework.beans.factory.annotation.Autowired;
8 | import org.springframework.beans.factory.annotation.Value;
9 | import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
10 | import org.springframework.context.annotation.Bean;
11 | import org.springframework.context.annotation.Configuration;
12 |
13 | @Configuration
14 | public class GrpcEurekaConfiguration {
15 |
16 | @Value("${grpc.eureka.service-id}")
17 | private String eurekaServiceId;
18 |
19 | @Autowired
20 | EurekaClientConfig eurekaClientConfig;
21 |
22 | @Bean
23 | @ConditionalOnMissingBean(ManagedChannel.class)
24 | public ManagedChannel defaultManagedChannel() {
25 |
26 | return ManagedChannelBuilder
27 | .forTarget("eureka://" + eurekaServiceId)
28 | .nameResolverFactory(new EurekaNameResolverProvider(eurekaClientConfig, "grpc.port"))
29 | .loadBalancerFactory(RoundRobinLoadBalancerFactory.getInstance())
30 | .usePlaintext(true)
31 | .build();
32 |
33 | }
34 |
35 | }
36 |
--------------------------------------------------------------------------------
/grpc-eureka-java/pom.xml:
--------------------------------------------------------------------------------
1 |
3 | 4.0.0
4 |
5 |
6 | com.github.exampledriven
7 | grpc-eureka-java-parent
8 | 1.0.0-SNAPSHOT
9 |
10 |
11 | grpc-eureka-java
12 | jar
13 |
14 | GRPC Eureka Java integration
15 |
16 | https://github.com/ExampleDriven/
17 |
18 | Eureka integration with GRPC
19 |
20 |
21 | Exampledriven
22 | exampledriven.wordpress.com
23 |
24 |
25 |
26 | Apache License, Version 2.0
27 | http://www.apache.org/licenses/LICENSE-2.0
28 |
29 |
30 |
31 |
32 |
33 | szantop
34 | Peter Szanto
35 | Exampledriven
36 | exampledriven.wordpress.com
37 |
38 | Project lead
39 |
40 |
41 |
42 |
43 |
44 |
45 | UTF-8
46 | 1.8
47 | 1.8
48 |
49 |
50 |
51 |
52 |
53 | com.google.inject
54 | guice
55 | 4.1.0
56 |
57 |
58 |
59 | com.netflix.eureka
60 | eureka-client
61 | 1.4.11
62 | provided
63 |
64 |
65 |
66 | io.grpc
67 | grpc-netty
68 | provided
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 | org.apache.maven.plugins
79 | maven-release-plugin
80 | 2.5.3
81 |
82 | true
83 | false
84 | release
85 | deploy
86 |
87 |
88 |
89 |
90 | org.apache.maven.plugins
91 | maven-compiler-plugin
92 | 3.7.0
93 |
94 | 1.8
95 | 1.8
96 |
97 |
98 |
99 |
100 |
101 |
102 |
--------------------------------------------------------------------------------
/grpc-eureka-java/src/main/java/org/exampledriven/grpc/eureka/EurekaNameResolver.java:
--------------------------------------------------------------------------------
1 | package org.exampledriven.grpc.eureka;
2 |
3 | import com.netflix.appinfo.ApplicationInfoManager;
4 | import com.netflix.appinfo.EurekaInstanceConfig;
5 | import com.netflix.appinfo.InstanceInfo;
6 | import com.netflix.appinfo.MyDataCenterInstanceConfig;
7 | import com.netflix.appinfo.providers.EurekaConfigBasedInstanceInfoProvider;
8 | import com.netflix.discovery.DiscoveryClient;
9 | import com.netflix.discovery.EurekaClient;
10 | import com.netflix.discovery.EurekaClientConfig;
11 | import com.netflix.discovery.shared.Application;
12 | import io.grpc.Attributes;
13 | import io.grpc.NameResolver;
14 | import io.grpc.ResolvedServerInfo;
15 |
16 | import java.net.InetSocketAddress;
17 | import java.net.URI;
18 | import java.util.Collections;
19 | import java.util.List;
20 | import java.util.stream.Collectors;
21 |
22 | public class EurekaNameResolver extends NameResolver {
23 |
24 | private final String serviceName;
25 | private final String portMetaData;
26 | private final EurekaClient eurekaClient;
27 |
28 | public EurekaNameResolver(EurekaClientConfig clientConfig, URI targetUri, String portMetaData) {
29 | this.portMetaData = portMetaData;
30 | serviceName = targetUri.getAuthority();
31 |
32 | MyDataCenterInstanceConfig instanceConfig = new MyDataCenterInstanceConfig();
33 |
34 | ApplicationInfoManager applicationInfoManager = initializeApplicationInfoManager(instanceConfig);
35 |
36 | eurekaClient = new DiscoveryClient(applicationInfoManager, clientConfig);
37 | }
38 |
39 | private static synchronized ApplicationInfoManager initializeApplicationInfoManager(EurekaInstanceConfig instanceConfig) {
40 | InstanceInfo instanceInfo = new EurekaConfigBasedInstanceInfoProvider(instanceConfig).get();
41 | return new ApplicationInfoManager(instanceConfig, instanceInfo);
42 | }
43 |
44 | @Override
45 | public String getServiceAuthority() {
46 | return serviceName;
47 | }
48 |
49 | @Override
50 | public void start(Listener listener) {
51 |
52 | update(listener);
53 |
54 | }
55 |
56 | private void update(Listener listener) {
57 | Application application = eurekaClient.getApplication(serviceName);
58 |
59 | List resolvedServerInfos = application.getInstances().stream().map(instanceInfo -> {
60 | int port;
61 | if (portMetaData != null) {
62 | String s = instanceInfo.getMetadata().get(portMetaData);
63 | port = Integer.parseInt(instanceInfo.getMetadata().get(portMetaData));
64 | } else {
65 | port = instanceInfo.getPort();
66 | }
67 | return new ResolvedServerInfo(new InetSocketAddress(instanceInfo.getHostName(), port), Attributes.EMPTY);
68 | }).collect(Collectors.toList());
69 |
70 | listener.onUpdate(Collections.singletonList(resolvedServerInfos), Attributes.EMPTY);
71 | }
72 |
73 | @Override
74 | public void shutdown() {
75 |
76 | }
77 | }
78 |
--------------------------------------------------------------------------------
/grpc-eureka-java/src/main/java/org/exampledriven/grpc/eureka/EurekaNameResolverProvider.java:
--------------------------------------------------------------------------------
1 | package org.exampledriven.grpc.eureka;
2 |
3 | import com.netflix.discovery.EurekaClientConfig;
4 | import io.grpc.Attributes;
5 | import io.grpc.NameResolver;
6 | import io.grpc.NameResolverProvider;
7 | import javax.annotation.Nullable;
8 | import java.net.URI;
9 |
10 | public class EurekaNameResolverProvider extends NameResolverProvider {
11 |
12 | protected static final String EUREKA = "eureka";
13 | private EurekaClientConfig eurekaClientConfig;
14 | private final String portMetaData;
15 |
16 | public EurekaNameResolverProvider(EurekaClientConfig eurekaClientConfig) {
17 | this(eurekaClientConfig, null);
18 | }
19 |
20 | public EurekaNameResolverProvider(EurekaClientConfig eurekaClientConfig, String portMetaData) {
21 | this.eurekaClientConfig = eurekaClientConfig;
22 | this.portMetaData = portMetaData;
23 | }
24 |
25 | @Override
26 | protected boolean isAvailable() {
27 | return true;
28 | }
29 |
30 | @Override
31 | protected int priority() {
32 | return 6;
33 | }
34 |
35 | @Nullable
36 | @Override
37 | public NameResolver newNameResolver(URI targetUri, Attributes params) {
38 | return new EurekaNameResolver(eurekaClientConfig, targetUri, portMetaData);
39 | }
40 |
41 | @Override
42 | public String getDefaultScheme() {
43 | return EUREKA;
44 | }
45 | }
46 |
--------------------------------------------------------------------------------
/pom.xml:
--------------------------------------------------------------------------------
1 |
3 | 4.0.0
4 |
5 | com.github.exampledriven
6 | grpc-eureka-java-parent
7 | 1.0.0-SNAPSHOT
8 | pom
9 |
10 | GRPC Eureka Java integration parent
11 |
12 | https://github.com/ExampleDriven/
13 |
14 | Eureka integration with GRPC
15 |
16 |
17 | Exampledriven
18 | exampledriven.wordpress.com
19 |
20 |
21 |
22 | Apache License, Version 2.0
23 | http://www.apache.org/licenses/LICENSE-2.0
24 |
25 |
26 |
27 |
28 | scm:git:git://github.com/ExampleDriven/grpc-eureka-java.git
29 | scm:git:git@github.com:ExampleDriven/grpc-eureka-java.git
30 | https://github.com/ExampleDriven/grpc-eureka-java
31 |
32 |
33 |
34 |
35 | szantop
36 | Peter Szanto
37 | Exampledriven
38 | exampledriven.wordpress.com
39 |
40 | Project lead
41 |
42 |
43 |
44 |
45 |
46 |
47 | UTF-8
48 | 1.8
49 | 1.8
50 | 0.15.0
51 |
52 |
53 |
54 |
55 |
56 | io.grpc
57 | grpc-netty
58 | ${grpc.verson}
59 |
60 |
61 |
62 | io.grpc
63 | grpc-stub
64 | ${grpc.verson}
65 |
66 |
67 |
68 | com.netflix.eureka
69 | eureka-client
70 | 1.4.11
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 | org.apache.maven.plugins
81 | maven-release-plugin
82 | 2.5.3
83 |
84 | true
85 | false
86 | release
87 | deploy
88 |
89 |
90 |
91 |
92 | org.apache.maven.plugins
93 | maven-compiler-plugin
94 | 3.7.0
95 |
96 | 1.8
97 | 1.8
98 |
99 |
100 |
101 |
102 |
103 |
104 |
105 | grpc-eureka-java
106 | grpc-eureka-java-starter
107 |
108 |
109 |
110 |
111 | oss.sonatype.org
112 | https://oss.sonatype.org/service/local/staging/deploy/maven2/
113 |
114 |
115 | oss.sonatype.org
116 | https://oss.sonatype.org/content/repositories/snapshots
117 |
118 |
119 |
120 |
121 |
122 | run-its
123 |
124 |
125 |
126 |
127 | org.apache.maven.plugins
128 | maven-invoker-plugin
129 | 2.0.0
130 |
131 | true
132 | ${project.build.directory}/it
133 |
134 | */pom.xml
135 |
136 | verify
137 | ${project.build.directory}/local-repo
138 | src/it/srunettings.xml
139 |
140 | clean
141 | test-compile
142 |
143 |
144 |
145 |
146 | integration-test
147 |
148 | install
149 | integration-test
150 | verify
151 |
152 |
153 |
154 |
155 |
156 |
157 |
158 |
159 |
160 |
161 | release
162 |
163 |
164 | performRelease
165 | true
166 |
167 |
168 |
169 |
170 |
171 | org.apache.maven.plugins
172 | maven-source-plugin
173 |
174 |
175 | attach-sources
176 |
177 | jar-no-fork
178 |
179 |
180 |
181 |
182 | jar
183 |
184 |
185 |
186 |
187 |
188 | org.apache.maven.plugins
189 | maven-gpg-plugin
190 | 1.5
191 |
192 |
193 | sign-artifacts
194 | verify
195 |
196 | sign
197 |
198 |
199 |
200 |
201 |
202 |
203 |
204 |
205 |
206 |
207 |
208 |
--------------------------------------------------------------------------------