mirror of
https://github.com/corda/corda.git
synced 2024-12-27 08:22:35 +00:00
[ENT-1281]: Disable database.runMigration by default and enforce database version on startup. (#264)
* [ENT-1281]: set database.runMigration=false by default and add state check at startup * [ENT-1281]: attempt to fix tests * [ENT-1281]: attempt to fix tests * [ENT-1281]: set runMigration=true in the cordformation plugin * [ENT-1281]: attempt to fix tests * [ENT-1281]: attempt to fix tests * [ENT-1281]: attempt to fix tests * [ENT-1281]: fix formatting * [ENT-1281]: typo and javadocs * [ENT-1281]: small refactoring and added test for SchemaMigration * [ENT-1281]: update documentation to reflect changes * [ENT-1281]: fix tests after merge * [ENT-1339]: for h2, allow schemas without migrations to run (#294) * [ENT-1339]: for h2, allow schemas without migrations to run * [ENT-1339]: fix various migration issues and change author name * [ENT-1339]: add naming convention for migrations * [ENT-1339]: change naming convention to use hyphens * [ENT-1339]: change mapping of participants to be able to control the table name * [ENT-1339]: change FK names to <=30 for oracle 11g compatibility * [ENT-1339]: cmd line argument for migrations made consistent * [ENT-1339]: revert abstract state superclasses * Update db integration test setup - new tables. * Update db integration test setup - new tables. * [ENT-1339]: remove final from participants to allow table name config * [ENT-1339]: shortened pk * [ENT-1339]: revert constructor * [ENT-1339]: change getMigrationResource api to Nullable * fix compile error * [ENT-1281]: fix tests after merge * [ENT-1281]: fix tests after merge
This commit is contained in:
parent
3c8ebdedae
commit
12546c0a7c
@ -48,7 +48,8 @@ public class StandaloneCordaRPCJavaClientTest {
|
||||
port.getAndIncrement(),
|
||||
port.getAndIncrement(),
|
||||
true,
|
||||
Collections.singletonList(rpcUser)
|
||||
Collections.singletonList(rpcUser),
|
||||
true
|
||||
);
|
||||
|
||||
@Before
|
||||
|
@ -151,6 +151,7 @@ As a database migration tool, we use the open source library liquibase <http://
|
||||
|
||||
If migration is enabled, the database state is checked (and updated) during node startup. (After deploying a new version of the code that contains database migrations, they are executed at that point).
|
||||
Possible database changes range from schema changes to data changes.
|
||||
If migration is disabled (the default), then on node startup, the database "version" is checked if it is up-to-date with the deployed code.
|
||||
|
||||
Liquibase will create a table called ``DATABASECHANGELOG``, that will store useful information about each change ( like timestamp, description, user, md5 hash so it can't be changed, etc)
|
||||
We can also "tag" the database at each release to make rollback easier.
|
||||
@ -228,7 +229,7 @@ Usage:
|
||||
Configurations:
|
||||
|
||||
- To enable migration at startup, set:
|
||||
- database.runMigration = true // true by default
|
||||
- database.runMigration = true // false by default,
|
||||
|
||||
Command line arguments:
|
||||
|
||||
|
@ -87,6 +87,7 @@ class Node(private val project: Project) : CordformNode() {
|
||||
}
|
||||
|
||||
private fun configureProperties() {
|
||||
config = config.withValue("database.runMigration", ConfigValueFactory.fromAnyRef(true))
|
||||
config = config.withValue("rpcUsers", ConfigValueFactory.fromIterable(rpcUsers))
|
||||
if (notary != null) {
|
||||
config = config.withValue("notary", ConfigValueFactory.fromMap(notary))
|
||||
|
@ -17,6 +17,7 @@ import net.corda.finance.DOLLARS
|
||||
import net.corda.finance.flows.CashIssueAndPaymentFlow
|
||||
import net.corda.nodeapi.internal.crypto.CertificateAndKeyPair
|
||||
import net.corda.nodeapi.internal.network.NetworkParameters
|
||||
import net.corda.nodeapi.internal.persistence.DatabaseConfig
|
||||
import net.corda.testing.SerializationEnvironmentRule
|
||||
import net.corda.testing.common.internal.testNetworkParameters
|
||||
import net.corda.testing.driver.NodeHandle
|
||||
@ -136,7 +137,7 @@ class NodeRegistrationTest : IntegrationTest() {
|
||||
return NetworkManagementServer().apply {
|
||||
start(
|
||||
serverAddress,
|
||||
configureDatabase(makeTestDataSourceProperties()),
|
||||
configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true)),
|
||||
LocalSigner(intermediateCa.keyPair, arrayOf(intermediateCa.certificate, rootCaCert)),
|
||||
networkParameters,
|
||||
networkParameters?.let { NetworkMapConfig(cacheTimeout = timeoutMillis, signInterval = timeoutMillis) },
|
||||
|
@ -89,7 +89,7 @@ class SigningServiceIntegrationTest {
|
||||
@Test
|
||||
fun `Signing service signs approved CSRs`() {
|
||||
//Start doorman server
|
||||
val database = configureDatabase(makeTestDataSourceProperties())
|
||||
val database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true))
|
||||
|
||||
NetworkManagementServer().use { server ->
|
||||
server.start(NetworkHostAndPort(HOST, 0), database, networkMapServiceParameter = null, doormanServiceParameter = DoormanConfig(approveAll = true, approveInterval = 2.seconds.toMillis(), jiraConfig = null), updateNetworkParameters = null)
|
||||
@ -99,7 +99,7 @@ class SigningServiceIntegrationTest {
|
||||
doReturn(ALICE_NAME).whenever(it).myLegalName
|
||||
doReturn(URL("http://${doormanHostAndPort.host}:${doormanHostAndPort.port}")).whenever(it).compatibilityZoneURL
|
||||
}
|
||||
val signingServiceStorage = DBSignedCertificateRequestStorage(configureDatabase(makeTestDataSourceProperties()))
|
||||
val signingServiceStorage = DBSignedCertificateRequestStorage(configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true)))
|
||||
|
||||
val hsmSigner = givenSignerSigningAllRequests(signingServiceStorage)
|
||||
// Poll the database for approved requests
|
||||
@ -143,7 +143,7 @@ class SigningServiceIntegrationTest {
|
||||
@Test
|
||||
fun `DEMO - Create CSR and poll`() {
|
||||
//Start doorman server
|
||||
val database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig())
|
||||
val database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true))
|
||||
|
||||
NetworkManagementServer().use { server ->
|
||||
server.start(NetworkHostAndPort(HOST, 0), database, networkMapServiceParameter = null, doormanServiceParameter = DoormanConfig(approveAll = true, approveInterval = 2.seconds.toMillis(), jiraConfig = null), updateNetworkParameters = null)
|
||||
|
@ -38,9 +38,7 @@ fun configureDatabase(dataSourceProperties: Properties,
|
||||
val dataSource = HikariDataSource(config)
|
||||
|
||||
val schemas = setOf(NetworkManagementSchemaServices.SchemaV1)
|
||||
if (databaseConfig.runMigration) {
|
||||
SchemaMigration(schemas, dataSource, true, databaseConfig.schema).runMigration()
|
||||
}
|
||||
SchemaMigration(schemas, dataSource, true, databaseConfig).nodeStartup()
|
||||
|
||||
return CordaPersistence(dataSource, databaseConfig, schemas, config.dataSourceProperties.getProperty("url", ""), emptyList())
|
||||
}
|
||||
|
@ -10,6 +10,7 @@ import net.corda.core.identity.CordaX500Name
|
||||
import net.corda.nodeapi.internal.crypto.X509Utilities
|
||||
import net.corda.nodeapi.internal.persistence.CordaPersistence
|
||||
import net.corda.testing.internal.createDevNodeCaCertPath
|
||||
import net.corda.nodeapi.internal.persistence.DatabaseConfig
|
||||
import org.assertj.core.api.Assertions.assertThat
|
||||
import org.bouncycastle.pkcs.PKCS10CertificationRequest
|
||||
import org.bouncycastle.pkcs.jcajce.JcaPKCS10CertificationRequest
|
||||
@ -28,7 +29,7 @@ class PersistentCertificateRequestStorageTest : TestBase() {
|
||||
|
||||
@Before
|
||||
fun startDb() {
|
||||
persistence = configureDatabase(makeTestDataSourceProperties())
|
||||
persistence = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true))
|
||||
storage = PersistentCertificateRequestStorage(persistence)
|
||||
}
|
||||
|
||||
|
@ -12,6 +12,7 @@ import net.corda.nodeapi.internal.crypto.X509CertificateFactory
|
||||
import net.corda.nodeapi.internal.network.NetworkMap
|
||||
import net.corda.nodeapi.internal.network.SignedNetworkMap
|
||||
import net.corda.nodeapi.internal.persistence.CordaPersistence
|
||||
import net.corda.nodeapi.internal.persistence.DatabaseConfig
|
||||
import net.corda.testing.common.internal.testNetworkParameters
|
||||
import net.corda.testing.internal.TestNodeInfoBuilder
|
||||
import net.corda.testing.internal.createDevIntermediateCaCertPath
|
||||
@ -37,7 +38,7 @@ class PersistentNetworkMapStorageTest : TestBase() {
|
||||
val (rootCa, intermediateCa) = createDevIntermediateCaCertPath()
|
||||
rootCaCert = rootCa.certificate
|
||||
this.intermediateCa = intermediateCa
|
||||
persistence = configureDatabase(makeTestDataSourceProperties())
|
||||
persistence = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true))
|
||||
networkMapStorage = PersistentNetworkMapStorage(persistence, LocalSigner(intermediateCa.keyPair, arrayOf(intermediateCa.certificate, rootCaCert)))
|
||||
nodeInfoStorage = PersistentNodeInfoStorage(persistence)
|
||||
requestStorage = PersistentCertificateRequestStorage(persistence)
|
||||
|
@ -14,6 +14,7 @@ import net.corda.nodeapi.internal.crypto.CertificateType
|
||||
import net.corda.nodeapi.internal.crypto.X509CertificateFactory
|
||||
import net.corda.nodeapi.internal.crypto.X509Utilities
|
||||
import net.corda.nodeapi.internal.persistence.CordaPersistence
|
||||
import net.corda.nodeapi.internal.persistence.DatabaseConfig
|
||||
import net.corda.testing.internal.TestNodeInfoBuilder
|
||||
import net.corda.testing.internal.createDevIntermediateCaCertPath
|
||||
import net.corda.testing.internal.signWith
|
||||
@ -41,7 +42,7 @@ class PersistentNodeInfoStorageTest : TestBase() {
|
||||
val (rootCa, intermediateCa) = createDevIntermediateCaCertPath()
|
||||
rootCaCert = rootCa.certificate
|
||||
this.intermediateCa = intermediateCa
|
||||
persistence = configureDatabase(MockServices.makeTestDataSourceProperties())
|
||||
persistence = configureDatabase(MockServices.makeTestDataSourceProperties(), DatabaseConfig(runMigration = true))
|
||||
nodeInfoStorage = PersistentNodeInfoStorage(persistence)
|
||||
requestStorage = PersistentCertificateRequestStorage(persistence)
|
||||
}
|
||||
|
@ -18,7 +18,7 @@ const val NODE_DATABASE_PREFIX = "node_"
|
||||
|
||||
// This class forms part of the node config and so any changes to it must be handled with care
|
||||
data class DatabaseConfig(
|
||||
val runMigration: Boolean = true,
|
||||
val runMigration: Boolean = false,
|
||||
val transactionIsolationLevel: TransactionIsolationLevel = TransactionIsolationLevel.REPEATABLE_READ,
|
||||
val schema: String? = null,
|
||||
val exportHibernateJMXStatistics: Boolean = false
|
||||
|
@ -2,6 +2,7 @@ package net.corda.nodeapi.internal.persistence
|
||||
|
||||
import com.fasterxml.jackson.databind.ObjectMapper
|
||||
import liquibase.Contexts
|
||||
import liquibase.LabelExpression
|
||||
import liquibase.Liquibase
|
||||
import liquibase.database.Database
|
||||
import liquibase.database.DatabaseFactory
|
||||
@ -14,17 +15,34 @@ import net.corda.core.utilities.contextLogger
|
||||
import java.io.*
|
||||
import javax.sql.DataSource
|
||||
|
||||
class SchemaMigration(val schemas: Set<MappedSchema>, val dataSource: DataSource, val failOnMigrationMissing: Boolean, private val schemaName: String? = null) {
|
||||
class SchemaMigration(val schemas: Set<MappedSchema>, val dataSource: DataSource, val failOnMigrationMissing: Boolean, private val databaseConfig: DatabaseConfig) {
|
||||
|
||||
companion object {
|
||||
private val logger = contextLogger()
|
||||
}
|
||||
|
||||
fun generateMigrationScript(outputFile: File) = doRunMigration(PrintWriter(outputFile))
|
||||
/**
|
||||
* Main entry point to the schema migration.
|
||||
* Called during node startup.
|
||||
*/
|
||||
fun nodeStartup() = if (databaseConfig.runMigration) runMigration() else checkState()
|
||||
|
||||
fun runMigration() = doRunMigration()
|
||||
/**
|
||||
* will run the liquibase migration on the actual database
|
||||
*/
|
||||
fun runMigration() = doRunMigration(run = true, outputWriter = null, check = false)
|
||||
|
||||
private fun doRunMigration(outputWriter: Writer? = null) {
|
||||
/**
|
||||
* will write the migration to the outputFile
|
||||
*/
|
||||
fun generateMigrationScript(outputFile: File) = doRunMigration(run = false, outputWriter = PrintWriter(outputFile), check = false)
|
||||
|
||||
/**
|
||||
* ensures that the database is up to date with the latest migration changes
|
||||
*/
|
||||
fun checkState() = doRunMigration(run = false, outputWriter = null, check = true)
|
||||
|
||||
private fun doRunMigration(run: Boolean, outputWriter: Writer?, check: Boolean) {
|
||||
|
||||
// virtual file name of the changelog that includes all schemas
|
||||
val dynamicInclude = "master.changelog.json"
|
||||
@ -65,6 +83,7 @@ class SchemaMigration(val schemas: Set<MappedSchema>, val dataSource: DataSource
|
||||
|
||||
val liquibase = Liquibase(dynamicInclude, customResourceAccessor, getLiquibaseDatabase(JdbcConnection(connection)))
|
||||
|
||||
val schemaName: String? = databaseConfig.schema
|
||||
if (!schemaName.isNullOrBlank()) {
|
||||
if (liquibase.database.defaultSchemaName != schemaName) {
|
||||
logger.debug("defaultSchemaName=${liquibase.database.defaultSchemaName} changed to $schemaName")
|
||||
@ -79,10 +98,16 @@ class SchemaMigration(val schemas: Set<MappedSchema>, val dataSource: DataSource
|
||||
logger.info("liquibaseSchemaName=${liquibase.database.liquibaseSchemaName}")
|
||||
logger.info("outputDefaultSchema=${liquibase.database.outputDefaultSchema}")
|
||||
|
||||
if (outputWriter != null) {
|
||||
liquibase.update(Contexts(), outputWriter)
|
||||
} else {
|
||||
liquibase.update(Contexts())
|
||||
when {
|
||||
run && !check -> liquibase.update(Contexts())
|
||||
check && !run -> {
|
||||
val unRunChanges = liquibase.listUnrunChangeSets(Contexts(), LabelExpression())
|
||||
if (unRunChanges.isNotEmpty()) {
|
||||
throw Exception("There are ${unRunChanges.size} outstanding database changes that need to be run. Please use the provided tools to update the database.")
|
||||
}
|
||||
}
|
||||
(outputWriter != null) && !check && !run -> liquibase.update(Contexts(), outputWriter)
|
||||
else -> throw IllegalStateException("Invalid usage.")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -204,14 +204,14 @@ abstract class AbstractNode(val configuration: NodeConfiguration,
|
||||
fun generateDatabaseSchema(outputFile: String) {
|
||||
HikariDataSource(HikariConfig(configuration.dataSourceProperties)).use { dataSource ->
|
||||
val jdbcUrl = configuration.dataSourceProperties.getProperty("url", "")
|
||||
SchemaMigration(cordappLoader.cordappSchemas, dataSource, !isH2Database(jdbcUrl), configuration.database.schema).generateMigrationScript(File(outputFile))
|
||||
SchemaMigration(cordappLoader.cordappSchemas, dataSource, !isH2Database(jdbcUrl), configuration.database).generateMigrationScript(File(outputFile))
|
||||
}
|
||||
}
|
||||
|
||||
fun runDbMigration() {
|
||||
HikariDataSource(HikariConfig(configuration.dataSourceProperties)).use { dataSource ->
|
||||
val jdbcUrl = configuration.dataSourceProperties.getProperty("url", "")
|
||||
SchemaMigration(cordappLoader.cordappSchemas, dataSource, !isH2Database(jdbcUrl), configuration.database.schema).runMigration()
|
||||
SchemaMigration(cordappLoader.cordappSchemas, dataSource, !isH2Database(jdbcUrl), configuration.database).runMigration()
|
||||
}
|
||||
}
|
||||
|
||||
@ -887,7 +887,7 @@ fun configureDatabase(dataSourceProperties: Properties,
|
||||
val jdbcUrl = config.dataSourceProperties.getProperty("url", "")
|
||||
|
||||
if (databaseConfig.runMigration) {
|
||||
SchemaMigration(schemaService.schemaOptions.keys, dataSource, !isH2Database(jdbcUrl), databaseConfig.schema).runMigration()
|
||||
SchemaMigration(schemaService.schemaOptions.keys, dataSource, !isH2Database(jdbcUrl), databaseConfig).runMigration()
|
||||
}
|
||||
|
||||
return CordaPersistence(dataSource, databaseConfig, schemaService.schemaOptions.keys, jdbcUrl, attributeConverters)
|
||||
|
@ -32,7 +32,7 @@ class InteractiveShellTest {
|
||||
|
||||
@Before
|
||||
fun setup() {
|
||||
InteractiveShell.database = configureDatabase(MockServices.makeTestDataSourceProperties(), DatabaseConfig(), rigorousMock())
|
||||
InteractiveShell.database = configureDatabase(MockServices.makeTestDataSourceProperties(), DatabaseConfig(runMigration = true), rigorousMock())
|
||||
}
|
||||
|
||||
@After
|
||||
|
@ -49,7 +49,7 @@ class PersistentIdentityServiceTests {
|
||||
@Before
|
||||
fun setup() {
|
||||
identityService = PersistentIdentityService(DEV_ROOT_CA.certificate)
|
||||
database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(), identityService)
|
||||
database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true), identityService)
|
||||
}
|
||||
|
||||
@After
|
||||
|
@ -81,7 +81,7 @@ class ArtemisMessagingTests {
|
||||
doReturn(true).whenever(it).useAMQPBridges
|
||||
}
|
||||
LogHelper.setLevel(PersistentUniquenessProvider::class)
|
||||
database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(), rigorousMock())
|
||||
database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true), rigorousMock())
|
||||
networkMapCache = NetworkMapCacheImpl(PersistentNetworkMapCache(database, emptyList()), rigorousMock())
|
||||
}
|
||||
|
||||
|
@ -45,7 +45,7 @@ class DBCheckpointStorageTests {
|
||||
@Before
|
||||
fun setUp() {
|
||||
LogHelper.setLevel(PersistentUniquenessProvider::class)
|
||||
database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(), rigorousMock())
|
||||
database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true), rigorousMock())
|
||||
newCheckpointStorage()
|
||||
}
|
||||
|
||||
|
@ -40,7 +40,7 @@ class DBTransactionStorageTests {
|
||||
fun setUp() {
|
||||
LogHelper.setLevel(PersistentUniquenessProvider::class)
|
||||
val dataSourceProps = makeTestDataSourceProperties()
|
||||
database = configureDatabase(dataSourceProps, DatabaseConfig(), rigorousMock())
|
||||
database = configureDatabase(dataSourceProps, DatabaseConfig(runMigration = true), rigorousMock())
|
||||
newTransactionStorage()
|
||||
}
|
||||
|
||||
|
@ -108,7 +108,7 @@ class HibernateConfigurationTest {
|
||||
}
|
||||
}
|
||||
val schemaService = NodeSchemaService(extraSchemas = setOf(CashSchemaV1, SampleCashSchemaV2, SampleCashSchemaV3, DummyLinearStateSchemaV1, DummyLinearStateSchemaV2, DummyDealStateSchemaV1 ))
|
||||
database = configureDatabase(dataSourceProps, DatabaseConfig(), identityService, schemaService)
|
||||
database = configureDatabase(dataSourceProps, DatabaseConfig(runMigration = true), identityService, schemaService)
|
||||
database.transaction {
|
||||
hibernateConfig = database.hibernateConfig
|
||||
// `consumeCash` expects we can self-notarise transactions
|
||||
|
@ -44,7 +44,7 @@ class NodeAttachmentStorageTest {
|
||||
LogHelper.setLevel(PersistentUniquenessProvider::class)
|
||||
|
||||
val dataSourceProperties = makeTestDataSourceProperties()
|
||||
database = configureDatabase(dataSourceProperties, DatabaseConfig(), rigorousMock())
|
||||
database = configureDatabase(dataSourceProperties, DatabaseConfig(runMigration = true), rigorousMock())
|
||||
fs = Jimfs.newFileSystem(Configuration.unix())
|
||||
}
|
||||
|
||||
|
@ -0,0 +1,59 @@
|
||||
package net.corda.node.services.persistence
|
||||
|
||||
import com.zaxxer.hikari.HikariConfig
|
||||
import com.zaxxer.hikari.HikariDataSource
|
||||
import net.corda.node.internal.configureDatabase
|
||||
import net.corda.node.services.schema.NodeSchemaService
|
||||
import net.corda.nodeapi.internal.persistence.CordaPersistence
|
||||
import net.corda.nodeapi.internal.persistence.DatabaseConfig
|
||||
import net.corda.nodeapi.internal.persistence.SchemaMigration
|
||||
import net.corda.testing.internal.rigorousMock
|
||||
import net.corda.testing.node.MockServices
|
||||
import org.assertj.core.api.Assertions.assertThat
|
||||
import org.assertj.core.api.Assertions.assertThatExceptionOfType
|
||||
import org.junit.Test
|
||||
import java.math.BigInteger
|
||||
|
||||
class SchemaMigrationTest {
|
||||
|
||||
@Test
|
||||
fun `Ensure that runMigration is disabled by default`() {
|
||||
assertThat(DatabaseConfig().runMigration).isFalse()
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `Migration is run when runMigration is disabled, and database is H2`() {
|
||||
val dataSourceProps = MockServices.makeTestDataSourceProperties()
|
||||
val db = configureDatabase(dataSourceProps, DatabaseConfig(runMigration = false), rigorousMock())
|
||||
checkMigrationRun(db)
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `Migration is run when runMigration is enabled`() {
|
||||
val dataSourceProps = MockServices.makeTestDataSourceProperties()
|
||||
val db = configureDatabase(dataSourceProps, DatabaseConfig(runMigration = true), rigorousMock())
|
||||
checkMigrationRun(db)
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `Verification passes when migration is run as a separate step`() {
|
||||
val schemaService = NodeSchemaService()
|
||||
val dataSourceProps = MockServices.makeTestDataSourceProperties()
|
||||
|
||||
//run the migration on the database
|
||||
val migration = SchemaMigration(schemaService.schemaOptions.keys, HikariDataSource(HikariConfig(dataSourceProps)), true, DatabaseConfig())
|
||||
migration.runMigration()
|
||||
|
||||
//start the node with "runMigration = false" and check that it started correctly
|
||||
val db = configureDatabase(dataSourceProps, DatabaseConfig(runMigration = false), rigorousMock(), schemaService)
|
||||
checkMigrationRun(db)
|
||||
}
|
||||
|
||||
private fun checkMigrationRun(db: CordaPersistence) {
|
||||
//check that the hibernate_sequence was created which means the migration was run
|
||||
db.transaction {
|
||||
val value = this.session.createNativeQuery("SELECT NEXT VALUE FOR hibernate_sequence").uniqueResult() as BigInteger
|
||||
assertThat(value).isGreaterThan(BigInteger.ZERO)
|
||||
}
|
||||
}
|
||||
}
|
@ -69,7 +69,7 @@ class HibernateObserverTests {
|
||||
return parent
|
||||
}
|
||||
}
|
||||
val database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(), rigorousMock(), schemaService)
|
||||
val database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true), rigorousMock(), schemaService)
|
||||
HibernateObserver.install(rawUpdatesPublisher, database.hibernateConfig, schemaService)
|
||||
database.transaction {
|
||||
val MEGA_CORP = TestIdentity(CordaX500Name("MegaCorp", "London", "GB")).party
|
||||
|
@ -88,7 +88,7 @@ class DistributedImmutableMapTests {
|
||||
private fun createReplica(myAddress: NetworkHostAndPort, clusterAddress: NetworkHostAndPort? = null): CompletableFuture<Member> {
|
||||
val storage = Storage.builder().withStorageLevel(StorageLevel.MEMORY).build()
|
||||
val address = Address(myAddress.host, myAddress.port)
|
||||
val database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(), rigorousMock())
|
||||
val database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true), rigorousMock())
|
||||
databases.add(database)
|
||||
val stateMachineFactory = { DistributedImmutableMap(database, RaftUniquenessProvider.Companion::createMap) }
|
||||
|
||||
|
@ -29,7 +29,7 @@ class PersistentUniquenessProviderTests {
|
||||
@Before
|
||||
fun setUp() {
|
||||
LogHelper.setLevel(PersistentUniquenessProvider::class)
|
||||
database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(), rigorousMock())
|
||||
database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true), rigorousMock())
|
||||
}
|
||||
|
||||
@After
|
||||
|
@ -131,7 +131,7 @@ open class VaultQueryTests {
|
||||
@Ignore
|
||||
@Test
|
||||
fun createPersistentTestDb() {
|
||||
val database = configureDatabase(makePersistentDataSourceProperties(), DatabaseConfig(), identitySvc)
|
||||
val database = configureDatabase(makePersistentDataSourceProperties(), DatabaseConfig(runMigration = true), identitySvc)
|
||||
setUpDb(database, 5000)
|
||||
|
||||
database.close()
|
||||
|
@ -22,7 +22,7 @@ class ObservablesTests {
|
||||
private val toBeClosed = mutableListOf<Closeable>()
|
||||
|
||||
private fun createDatabase(): CordaPersistence {
|
||||
val database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(), rigorousMock())
|
||||
val database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true), rigorousMock())
|
||||
toBeClosed += database
|
||||
return database
|
||||
}
|
||||
|
@ -74,7 +74,7 @@ class NodeInterestRatesTest {
|
||||
|
||||
@Before
|
||||
fun setUp() {
|
||||
database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(), rigorousMock())
|
||||
database = configureDatabase(makeTestDataSourceProperties(), DatabaseConfig(runMigration = true), rigorousMock())
|
||||
database.transaction {
|
||||
oracle = createMockCordaService(services, NodeInterestRates::Oracle)
|
||||
oracle.knownFixes = TEST_DATA
|
||||
|
@ -107,7 +107,7 @@ open class MockServices private constructor(
|
||||
val transactionIsolationLevel = if (config.hasPath(TRANSACTION_ISOLATION_LEVEL)) TransactionIsolationLevel.valueOf(config.getString(TRANSACTION_ISOLATION_LEVEL))
|
||||
else TransactionIsolationLevel.READ_COMMITTED
|
||||
val schema = if (config.hasPath(SCHEMA)) config.getString(SCHEMA) else ""
|
||||
return DatabaseConfig(transactionIsolationLevel = transactionIsolationLevel, schema = schema)
|
||||
return DatabaseConfig(runMigration = true, transactionIsolationLevel = transactionIsolationLevel, schema = schema)
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -209,6 +209,7 @@ class DriverDSLImpl(
|
||||
baseDirectory = baseDirectory(name),
|
||||
allowMissingConfig = true,
|
||||
configOverrides = configOf(
|
||||
"database" to mapOf("runMigration" to "true"),
|
||||
"myLegalName" to name.toString(),
|
||||
"p2pAddress" to p2pAddress.toString(),
|
||||
"rpcAddress" to rpcAddress.toString(),
|
||||
@ -227,6 +228,7 @@ class DriverDSLImpl(
|
||||
baseDirectory = baseDirectory,
|
||||
allowMissingConfig = true,
|
||||
configOverrides = configOf(
|
||||
"database" to mapOf("runMigration" to "true"),
|
||||
"p2pAddress" to "localhost:1222", // required argument, not really used
|
||||
"compatibilityZoneURL" to compatibilityZoneURL.toString(),
|
||||
"myLegalName" to providedName.toString())
|
||||
@ -313,7 +315,8 @@ class DriverDSLImpl(
|
||||
baseDirectory = baseDirectory(name),
|
||||
allowMissingConfig = true,
|
||||
configOverrides = cordform.config + rpcAddress + notary + mapOf(
|
||||
"rpcUsers" to if (rpcUsers.isEmpty()) defaultRpcUserList else rpcUsers
|
||||
"rpcUsers" to if (rpcUsers.isEmpty()) defaultRpcUserList else rpcUsers,
|
||||
"database" to mapOf("runMigration" to "true")
|
||||
)
|
||||
))
|
||||
return startNodeInternal(config, webAddress, null, "200m", localNetworkMap)
|
||||
|
@ -91,6 +91,7 @@ abstract class NodeBasedTest(private val cordappPackages: List<String> = emptyLi
|
||||
baseDirectory = baseDirectory,
|
||||
allowMissingConfig = true,
|
||||
configOverrides = configOf(
|
||||
"database" to mapOf("runMigration" to "true"),
|
||||
"myLegalName" to legalName.toString(),
|
||||
"p2pAddress" to p2pAddress,
|
||||
"rpcAddress" to localPort[1].toString(),
|
||||
|
@ -14,7 +14,8 @@ class NodeConfig(
|
||||
val rpcPort: Int,
|
||||
val webPort: Int,
|
||||
val isNotary: Boolean,
|
||||
val users: List<User>
|
||||
val users: List<User>,
|
||||
val runMigration: Boolean = true
|
||||
) {
|
||||
companion object {
|
||||
val renderOptions: ConfigRenderOptions = ConfigRenderOptions.defaults().setOriginComments(false)
|
||||
@ -34,6 +35,7 @@ class NodeConfig(
|
||||
.withValue("webAddress", addressValueFor(webPort))
|
||||
.withValue("rpcAddress", addressValueFor(rpcPort))
|
||||
.withValue("rpcUsers", valueFor(users.map(User::toMap).toList()))
|
||||
.withValue("database", valueFor(mapOf("runMigration" to runMigration)))
|
||||
.withValue("useTestClock", valueFor(true))
|
||||
return if (isNotary) {
|
||||
config.withValue("notary", ConfigValueFactory.fromMap(mapOf("validating" to true)))
|
||||
|
Loading…
Reference in New Issue
Block a user