Hi Sanjay,
Will your webService be primarily composed of a single instance or a cluster of instances? It seems like for your usecase, you are looking to just get hold of a single instance (regardless of whether they are in a cluster), and as soon as a single instance is available, your want to be able to use this instance to make a webservice call.
The current eureka2 API exposes are pretty low level and assumes a generic case of multi instance clusters that can be load balanced around for making web service calls. You can achieve your goal (if it is what I assumed above) by directly using eureka2 in the following ways:
--- non-blocking ---
interestClient.forInterest(forApplications("myApp"))
.filter(new Func1<ChangeNotification<InstanceInfo>, Boolean>() {
@Override
public Boolean call(ChangeNotification<InstanceInfo> notification) {
// filter out all non-data and delete notifications
return notification.isDataNotification() && notification.getKind() != ChangeNotification.Kind.Delete;
}
})
.take(1)
.map(new Func1<ChangeNotification<InstanceInfo>, Object>() {
@Override
public Object call(ChangeNotification<InstanceInfo> notification) {
InstanceInfo info = notification.getData();
NetworkAddress address = ServiceSelector.selectBy().publicIp(true).returnNetworkAddress(info);
// make call on the address only when the instanceInfo is returned
}
});
--- blocking ---
InstanceInfo info = interestClient.forInterest(forApplications("myApp"))
.filter(new Func1<ChangeNotification<InstanceInfo>, Boolean>() {
@Override
public Boolean call(ChangeNotification<InstanceInfo> notification) {
// filter out all non-data and delete notifications
return notification.isDataNotification() && notification.getKind() != ChangeNotification.Kind.Delete;
}
})
.map(new Func1<ChangeNotification<InstanceInfo>, InstanceInfo>() {
@Override
public InstanceInfo call(ChangeNotification<InstanceInfo> notification) {
return notification.getData();
}
})
.take(1)
.toBlocking()
.firstOrDefault(null);
NetworkAddress address = ServiceSelector.selectBy().publicIp(true).returnNetworkAddress(info);
// make call on the address
you can also work with a list of server instances:
InstanceInfo info = interestClient.forInterest(forApplications("myApp"))
.compose(ChangeNotificationFunctions.<InstanceInfo>buffers())
.compose(ChangeNotificationFunctions.<InstanceInfo>snapshots())
.take(1)
.map(new Func1<LinkedHashSet<InstanceInfo>, Object>() {
@Override
public Object call(LinkedHashSet<InstanceInfo> instanceInfos) {
// work with a latest snapshot list of servers for the app
}
});
We also want to provide some higher level APIs within eureka to make certain use cases easier, and any feedback you can provide on that would be very appreciated.
I would also encourage you to combine the use of eureka with Ocelli loadbalancer (see
https://github.com/Netflix/ocelli). The integration with the rc.1 release of eureka2 is not quite ready yet (I can let you know when it is), but the intended goal is that you should be able to feed an eureka2 interest stream into the ocelli loadbalancer, and from there you can just query the loadbalancer to return the next "best available" server to make queries to. The LB will provide a lot of additional value such as loadbalancing, failure detection etc.
Thanks,
David