I have implemented an API gateway with Spring cloud gateway. I have added the Redis rate limiters with below configurations:
spring:
cloud:
gateway:
discovery:
locator:
enabled: true
routes:
- id: user-service
uri: lb://user-service
predicates:
- Path=/user/**
filters:
- StripPrefix=1
- name: RequestRateLimiter
args:
key-resolver: "#{#remoteAddrKeyResolver}"
redis-rate-limiter.replenishRate: 1
redis-rate-limiter.burstCapacity: 5
---
spring:
redis:
host: localhost
port: 6379
database: 0
I can successfully block the user requests with an error code 429 TOO Many requests.
Now, I want the same entry to be inserted into the Redis database so that I can analyze.
What configuration do I need to make?
I have visited a blog where he shows it but I couldn't find code related to it. Here is the a link to that blog.
Also, Can anyone explain the exact difference between replenishRate vs burstCapacity with some example? I am a bit confused here.
Related
I have a Spring Boot Application that uses kafka to produce and consume messages to/from other applications.
I implemented a new producer whose messages should be sent to different clients located in different development servers. Kafka configuration it's specificated in the application.yml of the project. This was the previous configuration:
spring:
kafka:
bootstrap-servers: server.a:port
producer:
properties:
client.rack: server.a
consumer:
clientId: a-client-id
groupId: a-group-id
properties:
client.rack: server.a
jaas:
options:
username: an-username
password: a-password
Now with the new producer I need to produce message to a second server, server.b so:
spring:
kafka:
bootstrap-servers:
- server.a:port
- server.b:port
producer:
properties:
client.rack:
- server.a
- server.b
consumer:
clientId: a-client-id
groupId: a-group-id
properties:
client.rack: server.a
jaas:
options:
username: an-username
password: a-password
However, this seems to be sending the produced messages to server.b only.
I'm not sure if my config it's wrong or not. As far as I read this seems to be the properly way of doing it but, obviously, I did something wrong because it's not working. Bit lost here.
This isn't how Kafka works. Clients always send to the leader broker. Leaders can exist on any rack, and clients cannot control where they send data other than that leader first, and then configure acks to allow for replication to other followers on other racks.
Also, client.rack is a string, not a list.
i want to integrate the vault on my java micro-service, it has been already integrated for other services in the project . i want to know what are the actions that i have to perform for integrationg it .. currently the steps that i thought for integration are..
1. add the dependency on pom.xml
2. add the key on vault server (dashboard)
3. add this on application.yml
spring.cloud.vault:
host: localhost
port: 8200
scheme: https
uri: https://localhost:8200
connection-timeout: 5000
read-timeout: 15000
config:
spring.config.import: vault://
i want to know these were the only steps for integration or somethings more i have to do
I'm using eureka and zull as client discovery and gateway.
But while testing applications, I found that the first request will take a very long time to get response.
I have read springcloud documentation and also checked for stackoverflow to find any solution.
But so far the solutions from google which I found did not solve the problem.
below is part of the configuration:
zuul:
ignored-headers:
- Vary
- Access-Control-Allow-Origin
ribbon:
eager-load:
enabled: true
routes:
resourceCenter:
path: /web-resource-center/**
serviceId: web-resource-center
stripPrefix: true
messageCenter:
path: /web-message-center/**
serviceId: web-message-center
stripPrefix: true
webSystem:
path: /web-system/**
serviceId: web-system
stripPrefix: true
security:
path: /web-security/**
serviceId: web-security
stripPrefix: true
taskCenter:
path: /web-task-center/**
serviceId: web-task-center
stripPrefix: true
ribbon:
eager-load:
enabled: true
clients:
- web-resource-center
- web-task-center
- web-security
- web-message-center
- web-system
while not configured, the request will take 2s-4s to get response.
I have configured ribbon and zuul to eager load ,and that may speed up the first request for about 50%
while , the requests after the first one will take only less than 100ms each, I don't know why.
Also one thing here to cunfuse me : If I set a feign request in a controller then request this controller the slow response will not happen. So, are there any mistakes I have made configuring my application.yml?
please help me please,thanks a lot!
I found this problem to, when I restart my micro service, the first request though gateway will take 2-3s, and then took less than 100ms. after I configure ribbon eager load, also tooks 600ms. I dont konw how to handle this problem.
Good day,
At this moment I am working on a very simple gateway that (for now) only needs to redirect incoming HTTP POST and GET requests.
THE SETUP:
The Eureka Server: the location where my Spring Boot microservices are registered;
The Spring Gateway: maps all incoming HTTP POST and GET requests and routes them to the proper microservice;
The Spring Boot microservices: doing just some thingies as requested :)
Note: I'm kinda new to this gateway stuff, just you know :).
The microservice is registered fine with the Eureka server. Its webbased GUI shows me that the instance "MY-MICRO-SERVICE" is registered with the Eureka server. Other (Spring Boot) services can use that name ("MY-MICRO-SERVICE") without issues, so for them it works fine. Just this gateway can't handle the instance name; it seems it only accepts IP addresses (which I just want to prevent, as the microservice can change from servers and therefor their IP address). And the Eureka server is not configured to only allow/use IP addresses.
THE ISSUE:
All runs smooth when the Gateway has a route that holds an IP address of the microservice. But what I want is to let the Gateway resolve the service ID from the Eureka server. And if I do that, it throws me a java.net.UnknownHostException: MY-MICRO-SERVICE: Temporary failure in name resoultion.
THE QUESTION:
Now why can't I use the name of the Spring application "MY-MICRO-SERVICE" (being the registered Spring Boot microservice) in the Spring Gateway (while that construction works fine when used in other microservices)? Can't a Yaml config file handle such instance names, just only IP addresses?
THE DETAILS
The gateway is mostly configured via a yaml config file. There is only one simple Java class that kicks off the gateway application. The routing is all set in the yaml config file.
The Spring Gateway application class
#SpringBootApplication
#EnableEurekaClient
public class MyGatewayApplication {
public static void main(String[] args) {
SpringApplication.run(MyGatewayApplication.class, args);
}
}
The Gateway Yaml configuration file (application.yml)
spring:
application:
name: my-gateway
cloud:
gateway:
discovery:
locator:
lowerCaseServiceId: true
enabled: true
globalcors:
corsConfigurations:
'[/**]':
allowedOrigins: "*"
allowedMethods:
- GET
- POST
routes:
- id: my_route
uri: http://MY-MICRO-SERVICE
predicates:
- Path=/test/**
server:
port: 8999
info:
app:
properties: dev
The Error
java.net.UnknownHostException: MY-MICRO-SERVICE: Temporary failure in name resolution
at java.base/java.net.Inet6AddressImpl.lookupAllHostAddr(Native Method) ~[na:na]
at java.base/java.net.InetAddress$PlatformNameService.lookupAllHostAddr(InetAddress.java:929) ~[na:na]
at java.base/java.net.InetAddress.getAddressesFromNameService(InetAddress.java:1515) ~[na:na]
at java.base/java.net.InetAddress$NameServiceAddresses.get(InetAddress.java:848) ~[na:na]
at java.base/java.net.InetAddress.getAllByName0(InetAddress.java:1505) ~[na:na]
at java.base/java.net.InetAddress.getAllByName(InetAddress.java:1364) ~[na:na]
at java.base/java.net.InetAddress.getAllByName(InetAddress.java:1298) ~[na:na]
at java.base/java.net.InetAddress.getByName(InetAddress.java:1248) ~[na:na]
at io.netty.util.internal.SocketUtils$8.run(SocketUtils.java:146) ~[netty-common-4.1.36.Final.jar:4.1.36.Final]
...
Issue has been fixed.
I changed the "http" to "lb" protocol and that fixed my issue. To my understanding, "lb" stands for LoadBalancing. I have no loadbalancer active on my local machine, but anyway: this works.
- POST
routes:
- id: my_route
uri: lb://MY-MICRO-SERVICE
predicates:
- Path=/test/**
I am not able to open H2 console on the web browser.
My jhipster application is running on 8088 port. In server logs I am getting that H2 database is available on port 18088.
Tried below.
http://localhost:18088/h2-console
Getting Below response.
Below are the details in application-dev.yml.
devtools:
restart:
enabled: true
additional-exclude: .h2.server.properties
livereload:
enabled: false # we use Webpack dev server + BrowserSync for livereload
jackson:
serialization:
indent-output: true
datasource:
type: com.zaxxer.hikari.HikariDataSource
url: jdbc:h2:mem:jhipstersampleapplication;DB_CLOSE_DELAY=-1;DB_CLOSE_ON_EXIT=FALSE
username: jhipsterSampleApplication
password:
hikari:
poolName: Hikari
auto-commit: false
h2:
console:
enabled: true
jpa:
database-platform: io.github.jhipster.domain.util.FixedH2Dialect
database: H2
show-sql: true
properties:
hibernate.id.new_generator_mappings: true
hibernate.connection.provider_disables_autocommit: true
hibernate.cache.use_second_level_cache: true
hibernate.cache.use_query_cache: false
hibernate.generate_statistics: false
Please Help me out with this.
Adding slash solved my problem http://localhost:8080/h2-console to http://localhost:8080/h2-console/
There are 2 different ports:
HTTP port 8088 for h2 web console, it's served by your web app (same as your REST API)
TCP port 18088 that can be used by other applications using JDBC, it can't be used from a browser. This port is opened in DatabaseConfiguration.java in your project
Go to root of the app url (Access Url that you see in the application start)
then type "/h2-console" in the end.
localhost:8081/services//h2-console
Ensure you are accessing the correct port (8088 in your case), and that you do not change jhipster's setting for h2.console.enabled.
http://localhost:8088/h2-console should work.