首页 > 解决方案 > 外键仅适用于 Spring JPA 项目中的某些模型

问题描述

我的 spring jpa 项目遇到了一个奇怪的问题。基本上对于我的一个模型,外键似乎没有按预期工作。在我的项目中,我有一个模型类“Player”和另一个“PlayerStats”。

在“玩家统计”中,我为单个玩家添加统计数据并将其存储在我的数据库中。我使用基本的 html 作为简单的 web 表单进行数据输入。这工作正常,但列“player_id”始终为 NULL。它不会打扰我,但我想在另一个表中显示每个玩家的个人统计数据,如果我无法解决这个问题,其他所有玩家的统计数据都可以查看。

然而,我已经为我的项目中的不同模型类设置了相同的方式,我没有问题。例如,我有一个用户模型类,其中“user_id”用作模型类“团队”和“玩家”中的外键。在那里没有看到任何问题。因此,非常感谢任何关于我哪里出错的帮助。

1. 播放器模型类

@Data
@Entity
@Table(name="User_Player")
public class Player implements Serializable {

@OneToOne
private User user;
private static final long serialVersionUID = 1L;

@Id
@GeneratedValue(strategy= GenerationType.AUTO)
private Long id;

private String playerName;
private String dob;
private String hometown;
private String weight;
private String height;
private Position position;



}

2. PlayerStats 模型

@Data
@Entity
@Table(name="Player_Stats")


public class PlayerStats implements Serializable {

@ManyToOne
private Player player;


private static final long serialVersionUID = 1L;

@Id
@GeneratedValue(strategy= GenerationType.AUTO)
private Long id;

private int td;
private int rushYards;
private int recYards;
private int returnYards;
private int throwingYards;
private int throwAttenpts;
private int throwSuccess;
private int receptions;
private int rushTD;
private int recTD;
private int fumbles;
private int fumblesRecovered;
private int forcedFumbles;
private int sacks;
private int puntsBlocked;
private int fgScored;
private int fgMissed;
private int punts;
private int tackle;

public Opponents opponents;
 }

3. PlayerStats 控制器

@Slf4j
@Controller
@SessionAttributes("PlayerStats")
 public class PlayerStatsController {

 private PlayerStatsRepository playerStatsRepository;

 public PlayerStatsController(PlayerStatsRepository playerStatsRepository) 
{this.playerStatsRepository = playerStatsRepository;}

@Autowired
PlayerStatsRepository service;

@GetMapping("/addPlayerStats/{id}")
public String showSignUpFormPlayer(Player player) {
    return "addPlayerStats";
}

@PostMapping("/addPlayerStats/{id}")
public String processPlayer(@Valid PlayerStats playerStats, BindingResult result, 
 SessionStatus sessionStatus,
                            @AuthenticationPrincipal Player player, Model model) {
    if (result.hasErrors()) {
        return "playerStats";
    }

    //playerStats.setPl(player);
    service.save(playerStats);
    model.addAttribute("playerStats", service.findAll());
    return "login";
    }

4. 用户模型

   @Entity
    @Data
    @NoArgsConstructor(access= AccessLevel.PRIVATE, force=true)
    @RequiredArgsConstructor
    public class User implements UserDetails {

    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue(strategy= GenerationType.AUTO)
    private Long id;
    private final String username;
    private final String password;
    //private final String fullname;


    @Override
    public Collection<? extends GrantedAuthority> getAuthorities() {
        return Arrays.asList(new SimpleGrantedAuthority("ROLE_USER"));
    }
    @Override
    public boolean isAccountNonExpired() {
        return true;
    }
    @Override
    public boolean isAccountNonLocked() {
        return true;
    }
    @Override
    public boolean isCredentialsNonExpired() {
        return true;
    }
    @Override
    public boolean isEnabled() {
        return true;
    }
  }

标签: javamysqlspringdatabasejpa

解决方案


正如 Sariq 所说,您应该将播放器设置为 playerStats。

playerStats.setPlayer(player);

另外我建议做的是在 PlayerStats 类中明确声明外键。通过使用 @JoinColumn 注释来做到这一点,并确保使用数据库中的确切名称。

@ManyToOne
@JoinColumn(name = "player_id") // player_id has to match your foreign key in the database
private Player player;

推荐阅读