feat: protect API endpoints with API key authentication
This commit is contained in:
@@ -34,3 +34,5 @@ build/
|
|||||||
|
|
||||||
### Postgres ###
|
### Postgres ###
|
||||||
postgres-data/
|
postgres-data/
|
||||||
|
|
||||||
|
.env
|
||||||
|
|||||||
@@ -0,0 +1,46 @@
|
|||||||
|
package com.litoralregas.openvpn.security;
|
||||||
|
|
||||||
|
import jakarta.servlet.FilterChain;
|
||||||
|
import jakarta.servlet.ServletException;
|
||||||
|
import jakarta.servlet.http.HttpServletRequest;
|
||||||
|
import jakarta.servlet.http.HttpServletResponse;
|
||||||
|
import org.springframework.web.filter.OncePerRequestFilter;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
public class ApiKeyFilter extends OncePerRequestFilter {
|
||||||
|
|
||||||
|
private static final String HEADER = "X-API-Key";
|
||||||
|
|
||||||
|
private final ApiKeyProperties properties;
|
||||||
|
|
||||||
|
public ApiKeyFilter(ApiKeyProperties properties) {
|
||||||
|
this.properties = properties;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void doFilterInternal(
|
||||||
|
HttpServletRequest request,
|
||||||
|
HttpServletResponse response,
|
||||||
|
FilterChain filterChain
|
||||||
|
) throws ServletException, IOException {
|
||||||
|
|
||||||
|
String path = request.getRequestURI();
|
||||||
|
|
||||||
|
// allow health or non-api paths if needed
|
||||||
|
if (!path.startsWith("/api")) {
|
||||||
|
filterChain.doFilter(request, response);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
String apiKey = request.getHeader(HEADER);
|
||||||
|
|
||||||
|
if (apiKey == null || !apiKey.equals(properties.getApiKey())) {
|
||||||
|
response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
|
||||||
|
response.getWriter().write("{\"error\":\"Unauthorized\"}");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
filterChain.doFilter(request, response);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,17 @@
|
|||||||
|
package com.litoralregas.openvpn.security;
|
||||||
|
|
||||||
|
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||||
|
|
||||||
|
@ConfigurationProperties(prefix = "security")
|
||||||
|
public class ApiKeyProperties {
|
||||||
|
|
||||||
|
private String apiKey;
|
||||||
|
|
||||||
|
public String getApiKey() {
|
||||||
|
return apiKey;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setApiKey(String apiKey) {
|
||||||
|
this.apiKey = apiKey;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,15 @@
|
|||||||
|
package com.litoralregas.openvpn.security;
|
||||||
|
|
||||||
|
import org.springframework.boot.context.properties.EnableConfigurationProperties;
|
||||||
|
import org.springframework.context.annotation.Bean;
|
||||||
|
import org.springframework.context.annotation.Configuration;
|
||||||
|
|
||||||
|
@Configuration
|
||||||
|
@EnableConfigurationProperties(ApiKeyProperties.class)
|
||||||
|
public class SecurityConfig {
|
||||||
|
|
||||||
|
@Bean
|
||||||
|
public ApiKeyFilter apiKeyFilter(ApiKeyProperties properties) {
|
||||||
|
return new ApiKeyFilter(properties);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -34,4 +34,7 @@ lr:
|
|||||||
|
|
||||||
openvpn:
|
openvpn:
|
||||||
tools-path: ${LR_OPENVPN_TOOLS_PATH:/var/litoral_regas_openvpn/tools}
|
tools-path: ${LR_OPENVPN_TOOLS_PATH:/var/litoral_regas_openvpn/tools}
|
||||||
provision-dry-run: ${LR_OPENVPN_PROVISION_DRY_RUN:true}
|
provision-dry-run: ${LR_OPENVPN_PROVISION_DRY_RUN:true}
|
||||||
|
|
||||||
|
security:
|
||||||
|
api-key: ${API_KEY}
|
||||||
Reference in New Issue
Block a user