2015-05-16 3 views
0

Я читал об управлении транзакциями весной, используя аннотацию @Transactional в наших методах обслуживания или классе обслуживания и настраивая нашу транзакцию с ее атрибутами распространения, изоляции, таймаута, readOnly. Теперь я задаю вопрос:Синхронизация и @Transactional меня смущает

1) Нужно ли использовать синхронизацию (используя синхронизированное ключевое слово) или многопоточность, если мы используем @Transactional для достижения свойств ACID?

2) Какими могут быть различные сценарии, по-прежнему использующие многопоточность java в нашем веб-приложении Java EE?

3) Если требуется многопоточность, какой слой нашего приложения должен использовать синхронизированные методы или блоки и каковы могут быть причины этого?

Я изучаю с помощью фиктивного проекта онлайн-банкинга, который я нашел в github. Поэтому было бы неплохо, если бы ответы были связаны с этим сценарием. Так вот мои классы (просто чтобы дать вам идею):

//Here are some entity classes 

@Entity общественного класса User {...}

@Entity pulic класса Account {...}

@Entity класса Card общественного {...}

@Entity общественный класс Операция {...}

// now some DAO examples 

общественного класс OperationDaoImpl реализует OperationDao {

Page findNonCardByAccountIdAndYearMonth (Integer ACCOUNTID, годМесяц годМесяца, выгружаемый выгружаемый) {...}

Page findTransferByAccountId (Integer ACCOUNTID, выгружаемые выгружаемая) {...} DateTime getLastOperationDate() {...}

}

// now some service examples 

@Service

@Transactional (доступен только для чтения = истина)

@Validated

общественного класса BankServiceImpl реализует BankService {

общественности Карта sumResolvedCardOperationsByAccountIdAndYearMonth (Integer ACCOUNTID, годМесяц годМесяц) {...}

@Transactional (readOnly = false)

public void performTransfer (Integer debitedAccountId, Integer creditedAccountId, @Min (10) BigDecimal сумма) бросает UnsufficientBalanceException {...}

}

// и есть весна-контроллеры MVC.

Ребята! извините за то, что этот вопрос так долго.Любое предложение приветствуется. Благодарю.

ответ

4

Веб-приложение является многопоточным по своей природе, без необходимости запускать потоки: каждый раз, когда запрос поступает на веб-сервер, веб-сервер использует поток для обработки этого запроса. Если второй запрос приходит, пока первый обрабатывается, другой поток используется для обработки второго запроса одновременно с первым. Таким образом, контейнер обрабатывает многопоточность для вас.

Так что да, ваш BankService будет использоваться несколькими потоками одновременно. Означает ли это, что вам нужно использовать синхронизацию? Нет, совсем нет. Служба Spring обычно не имеет состояния, и никакое состояние, таким образом, не разделяется между потоками, что означает, что синхронизация не требуется. Единственным состоянием, которое используется несколькими потоками, является сама база данных. И здесь необходимы транзакции: они гарантируют, что, хотя база данных будет обрабатывать несколько запросов и обновлений одновременно, каждая транзакция будет выполняться изолированно от других и что состояние базы данных после фиксации будет согласовано.

Обратите внимание, что каждая транзакция будет иметь свой собственный контекст сохранения JPA, содержащий свои собственные экземпляры объектов JPA. Таким образом, даже если объекты JPA имеют состояние в памяти, они не разделяются между потоками и, следовательно, также не требуют синхронизации.

Также обратите внимание, что синхронизация не используется, как вы говорите, для повышения производительности. Синхронизация используется для обеспечения правильности.

+0

JB Nizet Спасибо, что освободили это. Но если возможно, вы могли бы очистить мое замешательство по поводу моего третьего вопроса (я изменил его часть). Я знаю, что это может быть длинный ответ. Если возможно, пришлите мне ссылку для изучения. –

+0

Пока у вас нет общего состояния, к которому нужно обращаться по одному потоку за раз, вам не нужна синхронизация. –