Skip to content

Add built-in support for Sort field whitelist validation #4178

@OKaluzny

Description

@OKaluzny

Problem

Currently, when an invalid sort field is passed to a Pageable parameter, Spring Data JPA throws PropertyReferenceException which results in HTTP 500 Internal Server Error. This has several issues:

1. Returns 500 instead of 400/422 - Invalid user input should return a client error, not server error
2. Security concern - Error messages can leak entity structure to clients
3. No whitelist support - All entity fields are allowed by default, but often only a subset should be sortable

Current Behavior

// Request: GET /tasks?sort=nonExistentField,asc

// Results in:
org.springframework.data.mapping.PropertyReferenceException:
No property 'nonExistentField' found for type TaskEntity
// HTTP 500 Internal Server Error

Expected Behavior

  @GetMapping("/tasks")                                                                                                                                                                                                    
  public Page<Task> getTasks(                                                                                                                                                                                              
      @AllowedSortFields({"createdAt", "name", "status"}) Pageable pageable                                                                                                                                                
  ) {                                                                                                                                                                                                                      
      return taskService.findAll(pageable);                                                                                                                                                                                
  }                                                                                                                                                                                                                        
                                                                                                                                                                                                                           
  // Request: GET /tasks?sort=nonExistentField,asc                                                                                                                                                                         
  // HTTP 422 Unprocessable Entity                                                                                                                                                                                         
  // {"error": "invalid-sort-field", "allowed": ["createdAt", "name", "status"]}      

Use Cases

  1. API Security - Restrict sortable fields to prevent information disclosure
  2. Performance - Only allow sorting on indexed columns
  3. Clean API contracts - Document allowed sort fields via annotation

Proposed Solution

Add an annotation like @AllowedSortFields that:

  • Validates sort parameters against a whitelist
  • Returns proper 4xx error with clear message
  • Integrates with HandlerMethodArgumentResolver for Pageable

Workaround

Currently developers must implement custom validation:

private static final Set<String> ALLOWED_SORT_FIELDS = Set.of("createdAt", "name");                                                                                                                                      
                                                                                                                                                                                                                         
public Page<Task> getAll(Pageable pageable) {                                                                                                                                                                            
    pageable.getSort().forEach(order -> {                                                                                                                                                                                
        if (!ALLOWED_SORT_FIELDS.contains(order.getProperty())) {                                                                                                                                                        
            throw new InvalidSortFieldException(order.getProperty());                                                                                                                                                    
        }                                                                                                                                                                                                                
    });                                                                                                                                                                                                                  
    // ...                                                                                                                                                                                                               
}  

This is boilerplate that could be eliminated with framework support.

Metadata

Metadata

Labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions