服务循环引用有多糟糕?
How bad is a service circular reference?
我有一个问题,它与我遇到的错误有关。在我的服务中使用循环引用到底有多糟糕?我很清楚错误的原因以及如何解决它,只是在我工作的公司中,一位资深人士建议我,对于交易问题,有必要进行这样的循环引用,实际上这是一个非常经常发生的问题在那里练习,但由于我是从头开始一个个人项目,这是我第一次得到错误,它再次引发了疑问。非常感谢您!
这是服务的代码
public class MedicalRecordServiceImpl implements MedicalRecordService {
private final MedicalRecordRepository medicalRecordRepository;
private final MedicalRecordService medicalRecordService;
private final PatientService patientService;
private final TutorService tutorService;
private final MedicalHistoryAnswerService medicalHistoryAnswerService;
private final DentalHistoryAnswerService dentalHistoryAnswerService;
public MedicalRecordServiceImpl(MedicalRecordRepository medicalRecordRepository, MedicalRecordService medicalRecordService, PatientService patientService, TutorService tutorService, MedicalHistoryAnswerService medicalHistoryAnswerService, DentalHistoryAnswerService dentalHistoryAnswerService) {
this.medicalRecordRepository = medicalRecordRepository;
this.medicalRecordService = medicalRecordService;
this.patientService = patientService;
this.tutorService = tutorService;
this.medicalHistoryAnswerService = medicalHistoryAnswerService;
this.dentalHistoryAnswerService = dentalHistoryAnswerService;
}
@Override
@Transactional(propagation = Propagation.REQUIRED)
public void saveMedicalRecord(MedicalRecordEntity medicalRecord) {
medicalRecordRepository.save(medicalRecord);
}
@Override
@Transactional(propagation = Propagation.REQUIRED)
public ResponseEntity<?> createNewMedicalRecord(MedicalRecordDTO medicalRecordDTO) {
PatientEntity patient = this.storeMedicalRecordIntoPatient(medicalRecordDTO);
TutorEntity tutor = this.storeMedicalRecordIntoTutor(medicalRecordDTO);
List<MedicalHistoryAnswerEntity> medicalHistoryAnswers = this.storeMedicalRecordIntoMedicalHisAns(medicalRecordDTO);
List<DentalHistoryAnswerEntity> dentalHistoryAnswers = this.storeMedicalRecordIntoDentalHisAns(medicalRecordDTO);
patientService.savePatient(patient);
tutor.setPatient(patient);
tutorService.saveTutor(tutor);
MedicalRecordEntity medicalRecord = this.createMedicalRecord(patient, tutor);
medicalRecordService.saveMedicalRecord(medicalRecord);
medicalHistoryAnswers.forEach(medicalHistoryAnswer -> {
medicalHistoryAnswer.setMedicalRecord(medicalRecord);
medicalHistoryAnswerService.saveMedicalHistoryAnswer(medicalHistoryAnswer);
});
dentalHistoryAnswers.forEach(dentalHistoryAnswer -> {
dentalHistoryAnswer.setMedicalRecord(medicalRecord);
dentalHistoryAnswerService.saveDentalHistoryAnswer(dentalHistoryAnswer);
});
return ResponseEntity.status(HttpStatus.OK).body("");
}
}
如您所说,我假设您知道错误是什么以及如何解决它。循环引用是错误的,原因如下:
Spring 在您启动项目时加载 beans,这意味着它以正确的顺序加载每个 bean,因此它可以加载所有 beans 并成功引用它们。如果你有一个循环引用 Spring 将不知道首先启动哪个 bean,因此会发生错误。这是关于 Spring 的工作原理。
我现在的项目也有这个错误,你不限于不做循环引用,你只需要指示Spring,这样它就知道在这些情况下如何处理每个bean。
好吧,想象一下:
你得到一个新的phone,你都为之兴奋。你想解锁它,但它受密码保护。密码在锁定的phone.
里面的笔记里面有
所以,您想使用您的 phone,为此您需要通行证。你想要通行证,为此你需要解锁 phone。您想使用您的phone,为此您需要您的通行证...等等
当你有循环引用时也会发生同样的情况,A你需要B,B你需要A,所以你不能创建A,也不能创建B,无法继续。
您可能需要循环依赖的唯一原因是您需要访问“this”作为 bean 以触发带注释的方法逻辑。
例如,如果您有两个方法“foo”(用@Transactional 注释)和“bar”(在其中调用“foo”)。如果调用 bar>foo (selfBean.foo() 而不是 this.foo()).
,您将不得不使用自我注入来触发事务
也可以使用@Lasy进行自注入,避免循环依赖错误。
但这是一个非常丑陋的解决方案,您应该尽可能避免使用它。这取决于情况,也许可以将逻辑拆分到不同的服务或使用 TransactionTemplate。
我有一个问题,它与我遇到的错误有关。在我的服务中使用循环引用到底有多糟糕?我很清楚错误的原因以及如何解决它,只是在我工作的公司中,一位资深人士建议我,对于交易问题,有必要进行这样的循环引用,实际上这是一个非常经常发生的问题在那里练习,但由于我是从头开始一个个人项目,这是我第一次得到错误,它再次引发了疑问。非常感谢您!
这是服务的代码
public class MedicalRecordServiceImpl implements MedicalRecordService {
private final MedicalRecordRepository medicalRecordRepository;
private final MedicalRecordService medicalRecordService;
private final PatientService patientService;
private final TutorService tutorService;
private final MedicalHistoryAnswerService medicalHistoryAnswerService;
private final DentalHistoryAnswerService dentalHistoryAnswerService;
public MedicalRecordServiceImpl(MedicalRecordRepository medicalRecordRepository, MedicalRecordService medicalRecordService, PatientService patientService, TutorService tutorService, MedicalHistoryAnswerService medicalHistoryAnswerService, DentalHistoryAnswerService dentalHistoryAnswerService) {
this.medicalRecordRepository = medicalRecordRepository;
this.medicalRecordService = medicalRecordService;
this.patientService = patientService;
this.tutorService = tutorService;
this.medicalHistoryAnswerService = medicalHistoryAnswerService;
this.dentalHistoryAnswerService = dentalHistoryAnswerService;
}
@Override
@Transactional(propagation = Propagation.REQUIRED)
public void saveMedicalRecord(MedicalRecordEntity medicalRecord) {
medicalRecordRepository.save(medicalRecord);
}
@Override
@Transactional(propagation = Propagation.REQUIRED)
public ResponseEntity<?> createNewMedicalRecord(MedicalRecordDTO medicalRecordDTO) {
PatientEntity patient = this.storeMedicalRecordIntoPatient(medicalRecordDTO);
TutorEntity tutor = this.storeMedicalRecordIntoTutor(medicalRecordDTO);
List<MedicalHistoryAnswerEntity> medicalHistoryAnswers = this.storeMedicalRecordIntoMedicalHisAns(medicalRecordDTO);
List<DentalHistoryAnswerEntity> dentalHistoryAnswers = this.storeMedicalRecordIntoDentalHisAns(medicalRecordDTO);
patientService.savePatient(patient);
tutor.setPatient(patient);
tutorService.saveTutor(tutor);
MedicalRecordEntity medicalRecord = this.createMedicalRecord(patient, tutor);
medicalRecordService.saveMedicalRecord(medicalRecord);
medicalHistoryAnswers.forEach(medicalHistoryAnswer -> {
medicalHistoryAnswer.setMedicalRecord(medicalRecord);
medicalHistoryAnswerService.saveMedicalHistoryAnswer(medicalHistoryAnswer);
});
dentalHistoryAnswers.forEach(dentalHistoryAnswer -> {
dentalHistoryAnswer.setMedicalRecord(medicalRecord);
dentalHistoryAnswerService.saveDentalHistoryAnswer(dentalHistoryAnswer);
});
return ResponseEntity.status(HttpStatus.OK).body("");
}
}
如您所说,我假设您知道错误是什么以及如何解决它。循环引用是错误的,原因如下:
Spring 在您启动项目时加载 beans,这意味着它以正确的顺序加载每个 bean,因此它可以加载所有 beans 并成功引用它们。如果你有一个循环引用 Spring 将不知道首先启动哪个 bean,因此会发生错误。这是关于 Spring 的工作原理。
我现在的项目也有这个错误,你不限于不做循环引用,你只需要指示Spring,这样它就知道在这些情况下如何处理每个bean。
好吧,想象一下: 你得到一个新的phone,你都为之兴奋。你想解锁它,但它受密码保护。密码在锁定的phone.
里面的笔记里面有所以,您想使用您的 phone,为此您需要通行证。你想要通行证,为此你需要解锁 phone。您想使用您的phone,为此您需要您的通行证...等等
当你有循环引用时也会发生同样的情况,A你需要B,B你需要A,所以你不能创建A,也不能创建B,无法继续。
您可能需要循环依赖的唯一原因是您需要访问“this”作为 bean 以触发带注释的方法逻辑。
例如,如果您有两个方法“foo”(用@Transactional 注释)和“bar”(在其中调用“foo”)。如果调用 bar>foo (selfBean.foo() 而不是 this.foo()).
,您将不得不使用自我注入来触发事务也可以使用@Lasy进行自注入,避免循环依赖错误。
但这是一个非常丑陋的解决方案,您应该尽可能避免使用它。这取决于情况,也许可以将逻辑拆分到不同的服务或使用 TransactionTemplate。