Here are my ProjectController:
package db.lab6.projectmanagement.controller;
import db.lab6.projectmanagement.dto.MemberDto;
import db.lab6.projectmanagement.dto.ProjectDto;
import db.lab6.projectmanagement.entity.Member;
import db.lab6.projectmanagement.entity.Project;
import db.lab6.projectmanagement.service.ProjectService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;
import java.util.List;
import java.util.Set;
@RestController
@RequestMapping("/projects")
public class ProjectController {
private final ProjectService projectService;
@Autowired
public ProjectController(ProjectService projectService) {
this.projectService = projectService;
}
@GetMapping("/{projectId}")
private ResponseEntity<Project> getProject(@PathVariable Long projectId) {
return ResponseEntity.ok(projectService.findById(projectId));
}
@PostMapping
public ResponseEntity<Project> createProject(@RequestBody ProjectDto projectDto) {
return ResponseEntity.status(HttpStatus.CREATED).body(projectService.create(projectDto));
}
@GetMapping("/{projectId}/members")
public ResponseEntity<Set<Member>> getAllMembersFromProject(@PathVariable Long projectId) {
return ResponseEntity.ok(projectService.findMembers(projectId));
}
// other mappings
}
Here are my ProjectService:
package db.lab6.projectmanagement.service.impl;
import db.lab6.projectmanagement.dto.MemberDto;
import db.lab6.projectmanagement.dto.ProjectDto;
import db.lab6.projectmanagement.entity.Member;
import db.lab6.projectmanagement.entity.Project;
import db.lab6.projectmanagement.entity.Role;
import db.lab6.projectmanagement.entity.User;
import db.lab6.projectmanagement.repository.MemberRepository;
import db.lab6.projectmanagement.repository.ProjectRepository;
import db.lab6.projectmanagement.service.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
@Service
public class ProjectServiceImpl implements ProjectService {
private final ProjectRepository projectRepository;
private final MemberRepository memberRepository;
private final UserService userService;
private final RoleService roleService;
@Autowired
public ProjectServiceImpl(ProjectRepository projectRepository,
MemberRepository memberRepository,
UserService userService,
RoleService roleService) {
this.projectRepository = projectRepository;
this.memberRepository = memberRepository;
this.userService = userService;
this.roleService = roleService;
}
@Override
public Project findById(Long id) {
return projectRepository.findById(id).orElseThrow(() ->
new ProjectNotFoundException(id));
}
@Override
public Project create(ProjectDto projectDto) {
User ownerUser = userService.findByNickname(projectDto.getOwnerNickname());
Role ownerRole = roleService.findByName("OWNER");
Member ownerMember = Member.builder()
.user(ownerUser)
.role(ownerRole).build();
Set<Member> members = new HashSet<>();
members.add(ownerMember);
Project project = Project.builder()
.name(projectDto.getName())
.description(projectDto.getDescription())
.members(members).build();
return projectRepository.save(project);
}
@Override
public Set<Member> findMembers(Long id) {
Project project = findById(id);
return project.getMembers();
}
// other methods
}
Project entity:
package db.lab6.projectmanagement.entity;
import com.fasterxml.jackson.annotation.JsonIgnore;
import jakarta.persistence.*;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.HashSet;
import java.util.Set;
@AllArgsConstructor
@NoArgsConstructor
@Data
@Builder
@Entity
@Table(name = "projects")
public class Project {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Column(nullable = false)
private String name;
private String description;
@OneToMany(mappedBy = "project", cascade = CascadeType.ALL, orphanRemoval = true, fetch = FetchType.LAZY)
@JsonIgnore
private Set<Task> tasks;
@ManyToMany(fetch = FetchType.EAGER, cascade = CascadeType.ALL)
@JoinTable(name = "project_member",
joinColumns = @JoinColumn(name = "project_id"),
inverseJoinColumns = @JoinColumn(name = "member_id"))
private Set<Member> members;
}
Member enitity:
package db.lab6.projectmanagement.entity;
import com.fasterxml.jackson.annotation.JsonIgnore;
import jakarta.persistence.*;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.HashSet;
import java.util.Set;
@AllArgsConstructor
@NoArgsConstructor
@Data
@Builder
@Entity
@Table(name = "members")
public class Member {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@ManyToOne(fetch = FetchType.EAGER)
@JoinColumn(name = "user_id", nullable = false)
private User user;
@ManyToOne(fetch = FetchType.EAGER)
@JoinColumn(name = "role_id", nullable = false)
private Role role;
@ManyToMany(mappedBy = "members", fetch = FetchType.EAGER)
@JsonIgnore
private Set<Project> projects;
}
When I create a project, I get a project that includes members
t.ex.
{
"id": 1,
"name": "foo name",
"description": "some description",
"members": [
{
"id": 1,
"user": {
"id": 1,
"email": "[email protected]",
"nickname": "dimitri",
"password": "123456"
},
"role": {
"id": 1,
"name": "OWNER"
}
}
]
}
But when I want to get the project I recieve
{
"id": 1,
"name": "foo name",
"description": "some description",
"members": []
}
The point is that the database contains a list of members tied to the project in project_member.
I tried to change fetch = FetchType.EAGER to FetchType.LAZY and vice versa but it didn’t help. I traced sql requests and they looked good. I even ran them in the database directly and it outputted everything correctly.
Here’s a trace of the sql request if needed
select
p1_0.id,
p1_0.description,
m1_0.project_id,
m1_1.id,
m1_1.role_id,
m1_1.user_id,
p1_0.name
from
projects p1_0
left join
project_member m1_0
on p1_0.id=m1_0.project_id
left join
members m1_1
on m1_1.id=m1_0.member_id
where
p1_0.id=?