Я очень новичок в разработке webapp в целом и Spring Framework в частности. Я следую этому руководству Spring JDBC Transactions. Но вместо доступа к службе db только из одного класса, я хочу получить к нему доступ из нескольких классов.
В учебнике служба определяется так:
public class BookingService {
@Autowired
JdbcTemplate jdbcTemplate;
@Transactional
public void book(String... persons) {
for (String person : persons) {
System.out.println("Booking " + person + " in a seat...");
jdbcTemplate.update("insert into BOOKINGS(FIRST_NAME) values (?)", person);
}
};
public List<String> findAllBookings() {
return jdbcTemplate.query("select FIRST_NAME from BOOKINGS", new RowMapper<String>()
@Override
public String mapRow(ResultSet rs, int rowNum) throws SQLException {
return rs.getString("FIRST_NAME");
}
});
}
}
Это бобы
@Configuration
@EnableTransactionManagement
@EnableAutoConfiguration
public class Application {
@Bean
BookingService bookingService() {
return new BookingService();
}
@Bean
DataSource dataSource() {
return new SimpleDriverDataSource() {{
setDriverClass(org.h2.Driver.class);
setUsername("sa");
setUrl("jdbc:h2:mem");
setPassword("");
}};
}
@Bean
JdbcTemplate jdbcTemplate(DataSource dataSource) {
JdbcTemplate jdbcTemplate = new JdbcTemplate(dataSource);
System.out.println("Creating tables");
jdbcTemplate.execute("drop table BOOKINGS if exists");
jdbcTemplate.execute("create table BOOKINGS(" +
"ID serial, FIRST_NAME varchar(5) NOT NULL)");
return jdbcTemplate;
}
Они создавали экземпляр службы только в классе Application и выполняли все транзакции
ApplicationContext ctx = SpringApplication.run(Application.class, args);
BookingService bookingService = ctx.getBean(BookingService.class);
//bookingService.doStuff()
В моем тестовом проекте я скопировал те же определения Bean, но я выполнил транзакции в нескольких классах.
public class foo {
ApplicationContext ctx = new AnnotationConfigApplicationContext(Application.class);
BookingService bookingService = ctx.getBean(BookingService.class);
bookingService.book(...);
// some other stuff
}
public class bar {
ApplicationContext ctx = new AnnotationConfigApplicationContext(Application.class);
BookingService bookingService = ctx.getBean(BookingService.class);
bookingService.findAllBookings(...);
// some other stuff
}
Кажется, что когда я выполняю все транзакции только в одном классе (например, книгу и нахожу в классе foo), он выполняет так, как ожидалось. Но когда я пытаюсь разделить их на несколько классов, он не ведет себя так, как ожидалось. Если я буду исполнять книгу в foo, я не могу найти в баре. Какую концепцию мне не хватает? Я создаю несколько экземпляров источника данных и jdbctemplate, потому что я создавал экземпляр службы несколько раз. Но я думал, что Весна справляется с инъекцией? И поскольку есть только одна физическая база данных, тогда будет только один экземпляр источника данных и jdbctemplate. Какую концепцию я неправильно понял? Пожалуйста, помогите и направьте меня в правильном направлении. Благодарю.
Вам нужно ввести свои зависимости, например:
public class Foo {
@Autowired
private BookingService bookingService;
public doStuff() {
bookingService.book(...);
// some other stuff
}
}