I'm using Spring Data Rest to expose a repository. I'm using @PreAuthorize
and @PostFilter
to restrict the access to the REST end points to exclusively admin users and filter the results.
@PreAuthorize("hasRole('ROLE_ADMIN')")
@PostFilter("hasPermission(filterObject, 'read')
public interface SomeRepository extends CrudRepository<SomeEntity, Long> {
}
At the same time I have another Controller that doesn't require any authentication but is using the repository.
@Controller
public class SomeController {
@Autowired
SomeRepository repository;
@RequestMapping(value = "/test")
public ResponseEntity test () {
// Do something
repository.findAll();
// Do something else
}
}
This doesn't work because the user that send the request to "/test" is not admin so it doesn't have access to the repository.
My question is, it is possible to add security exclusively to the REST interface of the repository and not when the repository is used internally in the application?
Thanks
This repository is an interface that lets you perform various operations involving Person objects. It gets these operations by extending the PagingAndSortingRepository interface that is defined in Spring Data Commons. At runtime, Spring Data REST automatically creates an implementation of this interface.
@RepositoryRestResource is used to set options on the public Repository interface - it will automatically create endpoints as appropriate based on the type of Repository that is being extended (i.e. CrudRepository/PagingAndSortingRepository/etc).
Spring Data REST can be used to expose HATEOAS RESTful resources around Spring Data repositories. Without writing a lot of code, we can expose RESTful API around Spring Data Repositories.
Each of these defines its own functionality: CrudRepository provides CRUD functions. PagingAndSortingRepository provides methods to do pagination and sort records. JpaRepository provides JPA related methods such as flushing the persistence context and delete records in a batch.
Please evaluate these possibilities:
RunAsManager
(or temporarily switching SecurityContext to perform a privileged operation)Securing modifying requests using REST event handlers:
@Service
@RepositoryEventHandler
public class FooService {
/**
* Handles before-* events.
*/
@HandleBeforeCreate
@HandleBeforeSave
@HandleBeforeDelete
@PreAuthorize("hasRole('ADMIN')")
public void onBeforeModify(final Foo entity){
// noop
}
/**
* Handles before-* events.
*/
@HandleBeforeLinkSave
@HandleBeforeLinkDelete
@PreAuthorize("hasRole('ADMIN')")
public void onBeforeModifyLink(final Foo entity, final Object linked){
// noop
}
}
Securing standard CRUD methods while adding non-secure custom methods on repository for internal use:
public interface FooDao extends CrudRepository<Foo, Long> {
@Override
@PreAuthorize("hasRole('ADMIN')")
<S extends Foo> S save(final S entity);
/**
* Saves entity without security checks.
*/
@Transactional
@Modifying
default <S extends Foo> S saveInternal(final S entity) {
return save(entity);
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With