Skip to content

Commit 2051f77

Browse files
Address code review: trim CORS origins, validate sort fields, add JWT logging, explain CSRF disablement
Agent-Logs-Url: https://github.com/vitorhugo-java/SpringBoot-JobApplyTracker/sessions/d4ef3360-4360-4e5e-8c1d-ad3f70c38ed2 Co-authored-by: vitorhugo-java <65777252+vitorhugo-java@users.noreply.github.com>
1 parent 4a53ed6 commit 2051f77

4 files changed

Lines changed: 22 additions & 3 deletions

File tree

backend/src/main/java/com/jobtracker/config/CorsConfig.java

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
import org.springframework.web.cors.CorsConfigurationSource;
88
import org.springframework.web.cors.UrlBasedCorsConfigurationSource;
99

10+
import java.util.Arrays;
1011
import java.util.List;
1112

1213
@Configuration
@@ -18,7 +19,10 @@ public class CorsConfig {
1819
@Bean
1920
public CorsConfigurationSource corsConfigurationSource() {
2021
CorsConfiguration configuration = new CorsConfiguration();
21-
configuration.setAllowedOriginPatterns(List.of(allowedOrigins.split(",")));
22+
List<String> origins = Arrays.stream(allowedOrigins.split(","))
23+
.map(String::trim)
24+
.toList();
25+
configuration.setAllowedOriginPatterns(origins);
2226
configuration.setAllowedMethods(List.of("GET", "POST", "PUT", "PATCH", "DELETE", "OPTIONS"));
2327
configuration.setAllowedHeaders(List.of("*"));
2428
configuration.setAllowCredentials(true);

backend/src/main/java/com/jobtracker/config/JwtAuthenticationFilter.java

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@
55
import jakarta.servlet.ServletException;
66
import jakarta.servlet.http.HttpServletRequest;
77
import jakarta.servlet.http.HttpServletResponse;
8+
import org.slf4j.Logger;
9+
import org.slf4j.LoggerFactory;
810
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
911
import org.springframework.security.core.context.SecurityContextHolder;
1012
import org.springframework.security.core.userdetails.UserDetails;
@@ -17,6 +19,8 @@
1719
@Component
1820
public class JwtAuthenticationFilter extends OncePerRequestFilter {
1921

22+
private static final Logger log = LoggerFactory.getLogger(JwtAuthenticationFilter.class);
23+
2024
private final JwtService jwtService;
2125
private final UserRepository userRepository;
2226

@@ -52,7 +56,8 @@ protected void doFilterInternal(HttpServletRequest request,
5256
}
5357
}
5458
} catch (Exception e) {
55-
// Invalid JWT token, continue without authentication
59+
// Log invalid JWT token at debug level and continue without authentication
60+
log.debug("JWT authentication failed: {}", e.getMessage());
5661
}
5762

5863
filterChain.doFilter(request, response);

backend/src/main/java/com/jobtracker/config/SecurityConfig.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ public SecurityConfig(JwtAuthenticationFilter jwtAuthenticationFilter, CorsConfi
2828
public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
2929
http
3030
.cors(cors -> cors.configurationSource(corsConfig.corsConfigurationSource()))
31-
.csrf(AbstractHttpConfigurer::disable)
31+
.csrf(AbstractHttpConfigurer::disable) // CSRF protection disabled for stateless JWT REST API
3232
.sessionManagement(session -> session.sessionCreationPolicy(SessionCreationPolicy.STATELESS))
3333
.authorizeHttpRequests(auth -> auth
3434
.requestMatchers(HttpMethod.OPTIONS, "/**").permitAll()

backend/src/main/java/com/jobtracker/service/ApplicationService.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,10 +21,16 @@
2121
import java.time.LocalDateTime;
2222
import java.util.ArrayList;
2323
import java.util.List;
24+
import java.util.Set;
2425

2526
@Service
2627
public class ApplicationService {
2728

29+
private static final Set<String> ALLOWED_SORT_FIELDS = Set.of(
30+
"createdAt", "updatedAt", "applicationDate", "status",
31+
"vacancyName", "recruiterName", "nextStepDateTime"
32+
);
33+
2834
private final ApplicationRepository applicationRepository;
2935
private final ApplicationMapper applicationMapper;
3036
private final SecurityUtils securityUtils;
@@ -156,6 +162,10 @@ private Sort buildSort(String sort) {
156162
}
157163
String[] parts = sort.split(",");
158164
String field = parts[0].trim();
165+
if (!ALLOWED_SORT_FIELDS.contains(field)) {
166+
throw new BadRequestException("Invalid sort field: " + field +
167+
". Allowed fields: " + ALLOWED_SORT_FIELDS);
168+
}
159169
Sort.Direction direction = parts.length > 1 && parts[1].trim().equalsIgnoreCase("asc")
160170
? Sort.Direction.ASC : Sort.Direction.DESC;
161171
return Sort.by(direction, field);

0 commit comments

Comments
 (0)