While working on spring Microservices I am not able to route api through zuul proxy
This is my code
eurka:
application.yml
spring:
application:
name: api
cloud:
config:
enabled: true
server:
port: ${PORT:8761}
eureka:
client:
registerWithEureka: false
fetchRegistry: false
serviceUrl:
defaultZone: http://${eureka.instance.hostname}:${server.port}/eureka/
instance:
hostname: localhost
zuul:
application.yml
spring:
application:
name: proxy-server
server:
port: 8079
eureka:
client:
serviceUrl:
defaultZone: http://localhost:8761/eureka
fetchRegistry: true
zuul:
ignored-services: '*'
prefix: /api
routes:
account:
path: /account/**
serviceId: account
stripPrefix: false
host:
socket-timeout-millis: 30000
ribbion:
eureka:
enabled: true
account
application.yml
ribbion:
eureka:
enabled: true
eureka:
instance:
preferIpAddress: true
client:
serviceUrl:
defaultZone: ${EUREKA_URI:http://localhost:8761/eureka}
instance:
preferIpAddress: true
dependency:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Finchley.SR1</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
Now the url localhost:8080/user/ is working fine but localhost:8080/api/account/user/ is throwing a 404.
Not sure what wrong I am doing here, any insight will be helpful please let me know if you need other details
What you need to do is,
Generate a Spring boot project with Zuul as a dependency.
Annotate the main class with #EnableZuulProxy
Configure routes and endpoints in application.properties file
Build and start the service
I suggest to implement the above steps first and make them work. Then customize that project as per your need. Found below article explaining the above steps with more details.
How to build an API-Gateway with Netflix Zuul + Spring Boot
I think you forgotten to add the name the of account service in account application.yml
spring:
application:
name: account
Related
I am working on a microservice project and implementing the Config Server using GitHub.
I created following files on GitHub-
Each file has the same configuration code (the common configuration for microservices) with different names-
spring:
application:
name: Config-default
eureka:
instance:
prefer-ip-address: true
client:
fetch-registry: true #true by default
register-with-eureka: true #true by default
service-url:
defaultZone: http://localhost:8761/eureka #url of the eureka server, registers with this url
I use the #EnableConfigServer annotation for the configuration server.
In the application.yml for the Configuration Server Microservice I add-
server:
port: 8089
spring:
application:
name: CONFIG-SERVER
cloud:
config:
server:
git:
uri: <github repository url>
clone-on-start: true
For the client microservices I added following dependency to pom.xml-
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-config</artifactId>
</dependency>
In the application.yml for the clients I add the configuration-
spring:
application:
name: USER-SERVICE #changes the name of application from UNKNOWN to UserService
config:
import: optional:configserver:http://localhost:8089
profiles:
active: prod
Problem- When I try to run my configuration server microservice I get the following error message-
***************************
APPLICATION FAILED TO START
***************************
Description:
Invalid config server configuration.
Action:
If you are using the git profile, you need to set a Git URI in your configuration. If you have set spring.cloud.config.server.bootstrap=true, you need to use a composite configuration.
Can somebody please help me find out the problem, why the URL is not detected.
I deployed Spring Boot Admin on an Azure Kubernetes Cluster. At first I get the pods of my app displayed as "UP". After restarting the deployment of the pods all pods are down and the new pods aren't recognized by Spring Boot Admin server. Is there anything I am missing?
Pods are UP as they should
New pods don't get registered and old are still on the dashboard
My application.yml
spring:
boot:
admin:
discovery:
enabled: true
monitor:
status-interval: 3s
status-lifetime: 3s
application:
name: monitoring-server
cloud:
kubernetes:
discovery:
primary-port-name: health
enabled: true
service-labels:
spring.boot: middleware
enabled: true
Main Class with annotations
#SpringBootApplication
#EnableAdminServer
#EnableDiscoveryClient
#EnableScheduling
public class MonitoringApplication {
public static void main(String[] args) {
SpringApplication.run(MonitoringApplication.class, args);
}
}
Added dependencies
<dependency>
<groupId>de.codecentric</groupId>
<artifactId>spring-boot-admin-starter-server</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-kubernetes-client-all</artifactId>
</dependency>
<dependency>
<groupId>de.codecentric</groupId>
<artifactId>spring-boot-admin-server-ui</artifactId>
</dependency>
Edit:
spring boot version: 2.6.6
spring boot admin version: 2.6.3
spring cloud version: 2021.0.1
Please try to activate the reloads.
spring:
cloud:
kubernetes:
reload:
enabled: true
Pom.xml:
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-boot-starter</artifactId>
<version>3.0.0</version>
</dependency>
<dependency>
<groupId>org.springdoc</groupId>
<artifactId>springdoc-openapi-ui</artifactId>
<version>1.6.7</version>
</dependency>
SwaggerConfig.java:
#Configuration
#RequiredArgsConstructor
public class SwaggerConfig {
private final RouteDefinitionLocator locator;
#Bean
public List<GroupedOpenApi> apis() {
List<GroupedOpenApi> groups = new ArrayList<>();
List<RouteDefinition> definitions = locator.getRouteDefinitions().collectList().block();
definitions.stream().filter(routeDefinition -> routeDefinition.getId().matches(".*-service")).forEach(routeDefinition -> {
String name = routeDefinition.getId().replaceAll("-service", "");
GroupedOpenApi api = GroupedOpenApi.builder().pathsToMatch("/" + name + "/**").group(name).build();
groups.add(api);
});
return groups;
}
}
application.yml:
gateway:
discovery:
locator:
enabled: true
lower-case-service-id: true
routes:
- id: swagger
uri: http://localhost:${server.port}
predicates:
- Path=/v3/api-docs/**
filters:
- RewritePath=/v3/api-docs/(?<path>.*), /$\{path}/v3/api-docs
- id: test-service
uri: lb://test-service
predicates:
- Path=/testservice/**
filters:
- RewritePath=/testservice/(?<path>.*), /$\{path}
Api gateway sees test-service with the help of discovery-server. When I enter swagger-ui of my gateway server,
in the "Select a definition" tab I only see "default" definition but no test-service definition that I really want. I've used those tutorials:
https://piotrminkowski.com/2020/02/20/microservices-api-documentation-with-springdoc-openapi/
https://dgempiuc.medium.com/api-gateway-swagger-composition-e9416398ca47
Screenshot:
I solved with this application.yml:
spring:
cloud:
gateway:
routes:
- id: openapi
uri: http://localhost:${server.port}
predicates:
- Path=/v3/api-docs/**
filters:
- RewritePath=/v3/api-docs/(?<path>.*), /$\{path}/v3/api-docs
- id: characters-service
uri: lb://characters-service
predicates:
- Path=/characters-service/**
filters:
- RewritePath=/characters-service/(?<path>.*), /$\{path}
springdoc:
enable-native-support: true
api-docs:
groups:
enabled: true
enabled: true
group-configs:
- group: api-gateway
packages-to-scan:
- dev.kambei.apigateway
display-name: API Gateway
- group: characters-service
paths-to-match:
- /characters-service/**
display-name: Characters Service
swagger-ui:
config-url: /v3/api-docs/swagger-config
url: /v3/api-docs
urls:
- url: /v3/api-docs
name: API Gateway
- url: /characters-service/v3/api-docs
name: Characters Service
you can add this config in the yaml fie
springdoc:
api-docs:
enabled: true
swagger-ui:
config-url: v3/api-docs/swagger-config
url: /v3/api-docs
urls:
- name: test
url: /v3/api-docs/test
I'm having trouble configuring a connection to Confluent when using spring-cloud-stream-binder-kafka. Possibly somebody can see what is wrong?
When I use the example from https://www.confluent.io/blog/schema-registry-avro-in-spring-boot-application-tutorial/
Then it works fine and I can see messages on Confluent Cloud
However, when adding the same connection details using the spring-cloud-stream-binder-kafka config, it is returning Unauthorized error.
Caused by: org.apache.kafka.common.errors.SerializationException: Error registering Avro schema: {"type":"record","name":"MySchema","namespace":"org.test","fields":[{"name":"value","type":"double"}]}
Caused by: io.confluent.kafka.schemaregistry.client.rest.exceptions.RestClientException: Unauthorized; error code: 401
My Configuration below gives the above error. Not sure what is going wrong?
cloud:
stream:
default:
producer:
useNativeEncoding: true
kafka:
binder:
brokers: myinstance.us-east1.gcp.confluent.cloud:9092
producer-properties:
key.serializer: org.apache.kafka.common.serialization.StringSerializer
value.serializer: io.confluent.kafka.serializers.KafkaAvroSerializer
schema.registry.url: https://myinstance.us-central1.gcp.confluent.cloud
basic.auth.credentials.source: USER_INFO
schema.registry.basic.auth.user.info: mySchemaKey:mySchemaSecret
configuration:
ssl.endpoint.identification.algorithm: https
sasl.mechanism: PLAIN
request.timeout.ms: 20000
retry.backoff.ms: 500
sasl.jaas.config: org.apache.kafka.common.security.plain.PlainLoginModule required username="myKey" password="MySecret";
security.protocol: SASL_SSL
bindings:
normals-out:
destination: normals
contentType: application/*+avro
Example from Confluent that is working fine:
kafka:
bootstrap-servers:
- myinstance.us-east1.gcp.confluent.cloud:9092
properties:
ssl.endpoint.identification.algorithm: https
sasl.mechanism: PLAIN
request.timeout.ms: 20000
retry.backoff.ms: 500
sasl.jaas.config: org.apache.kafka.common.security.plain.PlainLoginModule required username="myKey" password="MySecret";
security.protocol: SASL_SSL
schema.registry.url: https://myinstance.us-central1.gcp.confluent.cloud
basic.auth.credentials.source: USER_INFO
schema.registry.basic.auth.user.info: mySchemaKey:mySchemaSecret
producer:
key-serializer: org.apache.kafka.common.serialization.StringSerializer
value-serializer: io.confluent.kafka.serializers.KafkaAvroSerializer
template:
default-topic:
logging:
level:
root: info
My issue was only that I was missing a dependency in my pom.
I should delete my question, but I leave it here as a reference that the configuration does actually work as it is above.
<dependency>
<groupId>io.confluent</groupId>
<artifactId>kafka-schema-registry-client</artifactId>
<version>5.3.0</version>
</dependency>
I am trying to access the spring cloud config server but it is down. I still want to test the application using local application.properties. Is there any way i could do this?
pom.xml
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
<version>2.2.2.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-config</artifactId>
<version>2.2.2.RELEASE</version>
</dependency>
bootstrap.yml
server:
port: 8086
spring:
application:
name: PromoMS
security:
basic:
enabled: false
management:
security:
enabled: false
cloud:
config:
fail-fast: true
discovery:
enabled: true
service-id: ms-config-server
I am getting following exception
java.lang.IllegalStateException: No instances found of configserver (ms-config-server)
at org.springframework.cloud.config.client.ConfigServerInstanceProvider.getConfigServerInstances(ConfigServerInstanceProvider.java:48) ~[spring-cloud-config-client-2.2.2.RELEASE.jar:2.2.2.RELEASE]
To disable spring-cloud-config you and use your local properties, you need to add this property to your bootstrap.yml:
spring.cloud.config.enabled=false
And then enable it only when you need to run your application via application args, something like this:
java -jar your-application-name.jar --spring.cloud.config.enabled=true