Role based authorization with spring security 6.0.1 [closed] - java

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 6 days ago.
Improve this question
I am currently building a ecomerce web-application on java spring and i was wondering how can i create role based authorization.
The roles i have are USER and ADMIN.
The main reason for this is that i need to have logged user in the program
The logged user have a profile page
The admin has admin panel which should be only visible for admins.
dependencies {
implementation("org.springframework.boot:spring-boot-starter-data-jpa")//hibernate
implementation("org.springframework.boot:spring-boot-starter-hateoas")//otgovarq za ModelAndView
implementation("org.springframework.boot:spring-boot-starter-security:2.6.14")
implementation("org.springframework.boot:spring-boot-starter-web:2.6.14")
implementation("org.springframework.boot:spring-boot-starter-thymeleaf")//otgovarq za implementaciqta na cikli i tn v HTML-a
implementation("org.springframework.boot:spring-boot-starter-validation:3.0.2")//validaciqta
implementation("com.fasterxml.jackson.core:jackson-databind:2.14.2")//convert na obekt na string
implementation("org.thymeleaf.extras:thymeleaf-extras-springsecurity6")
implementation("nz.net.ultraq.thymeleaf:thymeleaf-layout-dialect:3.2.0")//otgovarq za layout page-a
implementation("mysql:mysql-connector-java:8.0.32")//vruzva bazata danni
implementation("org.modelmapper:modelmapper:3.1.1")//mapi ot VM na entity
implementation("javax.mail:mail:1.5.0-b01")//upravlqva mailservice-a
compileOnly("org.projectlombok:lombok")//anotaciite za geteri seteri i tn.
annotationProcessor("org.projectlombok:lombok")//gornoto cheti
testImplementation("org.springframework.boot:spring-boot-starter-test")
testImplementation("org.springframework.security:spring-security-test")
}
For now those are my Entities :
#MappedSuperclass
#NoArgsConstructor
public abstract class BaseEntity {
#Id
#GeneratedValue(generator = "uuid-string")
#GenericGenerator(name = "uuid-string",
strategy = "org.hibernate.id.UUIDGenerator")
private String id;
public String getId(){
return id;
}
public BaseEntity setId(String id){
this.id = id;
return this;
}
}
#Entity
#Table(name = "users")
#NoArgsConstructor
#AllArgsConstructor
#Getter
#Setter
public class User extends BaseEntity{
#Column
private String firstName;
#Column
private String lastName;
#Column
private String email;
#Column
private String password;
#ManyToMany
private List<UserRole> role;
#Column
private Date created;
}
#Entity
#Table(name = "roles")
#Getter
public class UserRole extends BaseEntity{
#Enumerated(EnumType.STRING)
private Role role;
public UserRole setRole(Role role) {
this.role = role;
return this;
}
}
I have implemented all the repositories, services and controllers.
In the end my question is how to make role based authorization with spring security 6.0.1

Related

Extra association table is created in spring boot

I'm currently working on developing a recipe application and I'm having trouble with DB table generation.
Here are the Entity files I'm using:
// Recipe.java
#Data
#Entity
#AllArgsConstructor
#NoArgsConstructor
#Table(name = "recipes")
public class Recipe {
#Id
#GeneratedValue
private int id;
private String name;
private String description;
private String instruction;
#ManyToOne
private User user;
#OneToMany(cascade=CascadeType.ALL)
private List<RecipeIngredient> ingredients = new ArrayList<>();
}
// Ingredient.java
#Data
#Entity
#AllArgsConstructor
#NoArgsConstructor
#Table(name = "ingredients")
public class Ingredient {
#Id
#GeneratedValue
private int id;
private String name;
}
// RecipeIngredient.java
#Data
#Entity
#AllArgsConstructor
#NoArgsConstructor
public class RecipeIngredient {
#Id
#GeneratedValue
private int id;
#ManyToOne
private Ingredient ingredient;
private String amount;
}
Spring Boot Automatically creates tables for me but I just wanna have one table for RecipeIngredient, but it creates two tables for them.
It works perfectly fine but the thing I want is just how to make these two tables into one or make spring boot not generate one of them.
If you want recipe_ingedients table only delete recipeIngredient Entity Class and if you want to keep recipe_ingredient table remove this:
#OneToMany(cascade=CascadeType.ALL)
private List<RecipeIngredient> ingredients = new ArrayList<>();

social network relationship using hibernate

I'm using JPA from SPRING and I'm having trouble creating this relationship for a social network.
I was a little confused.
can someone help me with this relationship?
#Entity(name = "tbl_user")
public class User {
#Id
private String id;
#ManyToMany
private List<User> friends;
}
#Entity(name = "tbl_friendship")
public class Friendship {
#Id
private String id;
#ManyToMany
private User source;
#ManyToMany
private User target;
}

Spring DATA - How to load a Collections of ids for an ManyToMany relation without load the whole LazyProxyObject [duplicate]

I have two Entities in my Spring-Boot Application:
User.java
#Entity
public class User {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
Long id;
String firstname;
String lastname;
String username;
String password;
}
and
Role.java
Entity
#Table(name = "role")
public class Role {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
Long id;
String name;
String description;
}
for my MySql database
I have excluded the getter and setter methods for this question.
I want to realise a Many-to-Many-Relationship between both Entities. Every user should be able to assign multiple roles to himself
I already Created a mapping table for both tables in my database. It has the rows
user_id
role_id.
I also created a new Entity UserRole.java which looks like this:
#Entity
#Table(name = "user_role")
public class UserRole implements Serializable{
private User user;
private Role role;
#Id
#ManyToOne
#JoinColumn(name = "user_id")
public User getuser() {
return user;
}
public void setUser(User user) {
this.user = user;
}
#Id
#ManyToOne
#JoinColumn(name = "role_id")
public Role getrole(){
return role;
}
public void setRole(Role role){
this.role = role;
}
}
Now my question: is this construction correct? If yes, how do i add existing roles to an existing user and get the roles of this user in spring-boot?
You can find any tutorial connected with many-to-many relationship using Hibernate/Spring Data, example:
Spring Data many-to-many
With your model it's simple to add the relationship mappings, like this:
#Entity
public class Role {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
private String name;
private String description;
#ManyToMany(cascade = CascadeType.ALL)
#JoinTable
private Set<User> users;
}
and this:
#Entity
public class User {
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
private String firstname;
private String lastname;
private String username;
private String password;
#ManyToMany(mappedBy = "users")
private Set<Role> roles;
}

Multiply ID mapping throw BaseEntity

I'm mapping classes via Hibernate and I need to map multiple ID for Relationship.
All ID's extend from BaseEntity. How can I implement multiple ID mapping for Relationship which contains Foreign Key for User in DataBase ?
Basicly fields userIdOne and userIdTwo in Relationship has to contain user's id which send request.
User extend own ID from BaseEntity.
Each time I run it - get en error:
This class [class com.mylov.springsocialnetwork.model.Relationship]
does not define an IdClass
#Getter
#Setter
#NoArgsConstructor
#AllArgsConstructor
#MappedSuperclass
#EqualsAndHashCode
public class BaseEntity implements Serializable {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
}
#Builder
#Getter
#Setter
#NoArgsConstructor
#AllArgsConstructor
#EqualsAndHashCode(exclude = {"posts"}, callSuper = false)
#Entity
public class User extends BaseEntity {
private String userName;
private String realName;
private String email;
private String phoneNumber;
private LocalDate birthDate;
#OneToMany(cascade = CascadeType.ALL, mappedBy = "userPosted")
private Set<Post> posts = new HashSet<>();
private String password;
public User(Long id, String userName, String realName, String email, String phoneNumber, LocalDate birthDate,
Set<Post> posts, String password) {
super(id);
this.userName = userName;
this.realName = realName;
this.email = email;
this.phoneNumber = phoneNumber;
this.birthDate = birthDate;
this.posts = posts;
this.password = password;
}
}
#Builder
#Getter
#Setter
#NoArgsConstructor
#AllArgsConstructor
#Entity
public class Relationship implements Serializable {
//#Id not working
private Long userIdFrom;
//#Id
private Long userIdTo;
#Enumerated(value = EnumType.STRING)
private RelationshipStatus status;
private LocalDate friendsRequestDate;
}
It appears that you are looking to establish a Relationship between two different users. This would mean that each Relationship is an object/entity of its own and should have its very own #Id (unrelated to user IDs).
The linkage to each User that form part of this Relationship should be mapped as foreign keys instead (probably #ManyToOne and a #JoinColumn).
For example:
#Entity
public class Relationship implements Serializable {
#Id
private Long relationshipId;
#ManyToOne(...)
#ForeignKey(name="FK_USER_ONE") //for generation only, it isn't strictly required
#JoinColumn(name="from")
private Long userIdFrom;
#ManyToOne(...)
#ForeignKey(name="FK_USER_TWO") //for generation only, it isn't strictly required
#JoinColumn(name="to")
private Long userIdTo;
#Enumerated(value = EnumType.STRING)
private RelationshipStatus status;
private LocalDate friendsRequestDate;
}
Edit:
It isn't required to specify the #ForeignKey annotations. They will be used if the database tables are generated automatically (ok for testing, but usually not something you'll want in production) and will create the FOREIGN KEY constraint on the table accordingly, but JPA mapping will work fine without it, because it takes the relationships from your defined model, not from the database itself.

Problem with receiving data from userRepository in spring-security + spring-data-jpa [duplicate]

This question already has answers here:
Infinite Recursion with Jackson JSON and Hibernate JPA issue
(29 answers)
Closed 3 years ago.
I really don't know how does the security and spring data jpa work, but when I try to receive other users data from database it's acting like an infinite loop and shows only my account info over 9k times and then after few seconds it crashes in web browser with error SyntaxError: JSON.parse: unterminated string literal at line 1 column 39978 of the JSON data,
My userRepository is a part of my UserDetailsServiceImplementation which is used in spring security as authentication with SQL database. It's work fine, I can log in on my account, but I can't query and view others' data info.
I've got no idea how to bypass it. Maybe it's a security feature to don't get access to other people credentials.
UserRepository
#Repository
public interface UserRepository extends JpaRepository<User, Long>{
public User findByUsername(String username);
#Query("SELECT * FROM user")
public List<User> findAll();
}
Controller
#RestController
#RequestMapping("/v1/api")
public class HomeApiController {
#Autowired
private UserRepository userRepository;
#GetMapping("/users")
public List<User> getUsers() {
return userRepository.findAll();
}
}
User
#Entity
#Table
public class User {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
#Column
private String username;
#Column
#JsonIgnore
private String password;
#Column
private boolean enabled;
#ManyToMany(fetch = FetchType.EAGER, cascade = CascadeType.ALL)
#JoinTable(name = "user_role", joinColumns = #JoinColumn(name = "user_id"), inverseJoinColumns = #JoinColumn(name = "role_id"))
private Set<Authority> authorities;
public User() {
}
then field based constructor + getters and setters
Authority
#Entity
#Table
public class Authority {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column
private Long id;
#Column
private String role;
#ManyToMany(mappedBy = "authorities")
private Set<User> user;
public Authority() {
}
field constructor + getters and setters
i expected to query and retrieve all other users in user table in database which is also used to authorize users based on roles in system.
json output shows...
{"id":1,"username":"Admin","enabled":true,"authorities":[{"role":"ROLE_USER","user":[{"id":1,"username":"Admin","enabled":true,"authorities":[{"role":"ROLE_USER","user":[{"id":1,"username":"Admin","enabled":true,"authorities":[{"role":"ROLE_USER","user":[{"id":1,"username":"Admin","enabled":true,"authorities":[{"role":"ROLE_USER","user":
and it's infinite nested.
i think there's something wrong with authorities
when i clear user_role table then output works great
id 1
username "Admin"
enabled true
authorities []
what's wrong?
you have to annotate the User set in the Authority class with #JsonIgnore or Annotate the Authorities set in the User class depending on what you need in your API call.
#Entity
#Table
public class User {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
#Column
private String username;
#Column
#JsonIgnore
private String password;
#Column
private boolean enabled;
#JsonIgnore
#ManyToMany(fetch = FetchType.EAGER, cascade = CascadeType.ALL)
#JoinTable(name = "user_role", joinColumns = #JoinColumn(name = "user_id"),
inverseJoinColumns = #JoinColumn(name = "role_id"))
private Set<Authority> authorities;
public User() {
}
Or
#Entity
#Table
public class Authority {
#Id
#GeneratedValue(strategy = GenerationType.IDENTITY)
#Column
private Long id;
#Column
private String role;
#JsonIgnore
#ManyToMany(mappedBy = "authorities")
private Set<User> user;
public Authority() {
}
EDIT: Also I do recommend using DTOs to minimize the coupling and avoid such problems

Categories