本文介紹了H2訪問數據庫以從單獨的線程訪問測試數據的處理方法,對大家解決問題具有一定的參考價值,需要的朋友們下面隨著小編來一起學習吧!
問題描述
我的集成測試場景:
-
在H2數據庫中創建行
sleep(50000ms)
(同時,由于Spring配置,將調用另一個線程,此線程應找到點1中創建的行,并更新此行)預期從點%1開始有行。已由點%2中提到的線程更新。
此方案同時測試配置和實現。這就是我想要實現的目標。
我在所有測試中都使用H2數據庫,因此決定在這里也使用它。在調試測試場景時,我發現sleep
期間調用的新線程連接到數據庫,但沒有找到創建的行。我瀏覽了H2文檔,并開始使用:
java -cp ~/.m2/repository/com/h2database/h2/1.4.194/h2-1.4.194.jar org.h2.tools.Server -tcp -web -browser -tcpAllowOthers -tcpPort 9092 -webPort 8082
和連接字符串:
DB_URL=jdbc:h2:tcp://localhost:9092/~/test2
和配置:
<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"
destroy-method="close" p:driverClassName="org.h2.Driver"
p:url="${DB_URL}"
p:username="${OPENSHIFT_MYSQL_DB_USERNAME}" p:password="${OPENSHIFT_MYSQL_DB_PASSWORD}"/>
<util:properties id="hibernateProperties">
<prop key="hibernate.dialect">org.hibernate.dialect.H2Dialect</prop>
<prop key="hibernate.hbm2ddl.auto">validate</prop>
<prop key="hibernate.show_sql">false</prop>
</util:properties>
<bean id="sessionFactory"
class="org.springframework.orm.hibernate5.LocalSessionFactoryBean"
p:dataSource-ref="dataSource" p:packagesToScan="com.fridayweekend.lottery.model"
p:hibernateProperties-ref="hibernateProperties"/>
<bean id="transactionManager"
class="org.springframework.orm.hibernate5.HibernateTransactionManager"
p:sessionFactory-ref="sessionFactory"/>
注意:我已經嘗試過DDL-AUTO-我在第一次試運行時嘗試創建架構,然后只驗證它(以防止重新創建),但是沒有幫助。
我可以通過H2 Web Console
檢查數據庫。我看到創建了Schema(基于我的帶Java注釋的模型),但是沒有數據(即使在sleep
或調試斷點期間)。
另一方面,當我手動添加數據(從第一個場景點開始)時,我可以調試第二個線程看到它并正確更新它,然后測試成功。來自第二個線程的數據是持久化的,即使在測試套件完成之后,我也可以看到它。
要使來自主線程(@Test注釋)的數據對第二個線程可見,我應該做些什么?
PS。我認為這無關緊要,但是”第二個”線程是這樣調用的:
<util:properties id="javaMailProperties">
<prop key="mail.imap.socketFactory.class">javax.net.ssl.SSLSocketFactory</prop>
<prop key="mail.imap.socketFactory.fallback">false</prop>
<prop key="mail.store.protocol">${imap.protocol}</prop>
<prop key="mail.debug">${imap.debug}</prop>
</util:properties>
<mail:inbound-channel-adapter id="imapAdapter"
store-uri="${imap.uri}"
channel="recieveEmailChannel"
should-delete-messages="false"
should-mark-messages-as-read="true"
auto-startup="true"
java-mail-properties="javaMailProperties">
<int:poller fixed-delay="${imap.poolerSecondsDelay}" time-unit="SECONDS"/>
</mail:inbound-channel-adapter>
<int:channel id="recieveEmailChannel">
<int:interceptors>
<int:wire-tap channel="logger"/>
</int:interceptors>
</int:channel>
<int:logging-channel-adapter id="logger" level="DEBUG"/>
<int:service-activator input-channel="recieveEmailChannel" ref="emailReceiverService" method="receive"/>
因此,它基本上調用emailReceiverService
bean的receive
方法。當然-我確保方法被調用(通過向收件箱發送電子郵件)-但是,正如我所說的-我不認為創建第二個線程的方式是相關的。基本上-它是由Spring配置調用的(Spring配置通過
傳遞給測試方法
@ContextConfiguration(locations = { "classpath:spring/test-lottery-context.xml", "classpath:spring/test-sms-context.xml" })
@Transactional
public class QueueServiceImplIntegrationTest extends AbstractTransactionalTestNGSpringContextTests {
)。
推薦答案
我在那里找到了根本問題:事務!
我的測試是擴展AbstractTransactionalTestNGSpringContextTests
,因此事務范圍是整個@Test
帶注釋的方法。我將測試更改為簡單地擴展AbstractTestNGSpringContextTests
-然后事務的范圍縮小到從@Test
注釋方法調用的特定服務方法(我說的是常規MVC模式)。這解決了我的問題。
干杯!
這篇關于H2訪問數據庫以從單獨的線程訪問測試數據的文章就介紹到這了,希望我們推薦的答案對大家有所幫助,