1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.kuali.common.impex.spring;
17
18 import java.sql.Connection;
19 import java.sql.SQLException;
20 import java.util.HashMap;
21 import java.util.Map;
22
23 import liquibase.database.Database;
24 import liquibase.exception.DatabaseException;
25 import liquibase.integration.commandline.CommandLineUtils;
26 import liquibase.snapshot.DatabaseSnapshot;
27 import liquibase.snapshot.InvalidExampleException;
28 import liquibase.snapshot.SnapshotControl;
29 import liquibase.snapshot.SnapshotGeneratorFactory;
30 import org.kuali.common.impex.liquibase.LiquibaseSchemaProvider;
31 import org.kuali.common.impex.model.Schema;
32 import org.kuali.common.impex.schema.MySqlSequenceFinder;
33 import org.kuali.common.impex.schema.OracleSequenceFinder;
34 import org.kuali.common.impex.schema.SequenceFinder;
35 import org.kuali.common.jdbc.context.DatabaseProcessContext;
36 import org.kuali.common.jdbc.spring.JdbcDataSourceConfig;
37 import org.kuali.common.util.FormatUtils;
38 import org.kuali.common.util.spring.SpringUtils;
39 import org.slf4j.Logger;
40 import org.slf4j.LoggerFactory;
41 import org.springframework.beans.factory.annotation.Autowired;
42 import org.springframework.context.annotation.Bean;
43 import org.springframework.context.annotation.Configuration;
44 import org.springframework.context.annotation.Import;
45 import org.springframework.core.env.Environment;
46
47 @Configuration
48 @Import({ JdbcDataSourceConfig.class })
49 public class LiquibaseSchemaConfig {
50
51 private static final Logger log = LoggerFactory.getLogger(LiquibaseSchemaConfig.class);
52
53 protected static final String DB_VENDOR_KEY = "db.vendor";
54
55 @Autowired
56 JdbcDataSourceConfig dataSourceConfig;
57
58 @Autowired
59 Environment env;
60
61 @Bean
62 public DatabaseSnapshot databaseSnapshot() throws DatabaseException, InvalidExampleException {
63
64
65 long start = System.currentTimeMillis();
66
67
68 DatabaseProcessContext context = dataSourceConfig.jdbcDatabaseProcessContext();
69
70
71 ClassLoader loader = getClass().getClassLoader();
72 String url = context.getUrl();
73 String username = context.getUsername();
74 String password = context.getPassword();
75 String driver = context.getDriver();
76
77 log.info("Creating Liquibase snapshot [{}] - [{}]", url, username);
78
79
80 Database database = CommandLineUtils.createDatabaseObject(loader, url, username, password, driver, null, username, null, null);
81
82
83 SnapshotGeneratorFactory factory = SnapshotGeneratorFactory.getInstance();
84 DatabaseSnapshot snapshot = factory.createSnapshot(database.getDefaultSchema(), database, new SnapshotControl());
85
86 Object[] args = { url, username, FormatUtils.getTime(System.currentTimeMillis() - start) };
87 log.info("Liquibase snapshot created [{}] - [{}] - Time: {}", args);
88
89 return snapshot;
90 }
91
92 @Bean
93 public Map<String, SequenceFinder> sequenceFinderMap() throws SQLException {
94 Map<String, SequenceFinder> result = new HashMap<String, SequenceFinder>();
95
96 result.put(OracleSequenceFinder.SUPPORTED_VENDOR, oracleSequenceFinder());
97 result.put(MySqlSequenceFinder.SUPPORTED_VENDOR, mysqlSequenceFinder());
98
99 return result;
100 }
101
102 @Bean
103 public LiquibaseSchemaProvider liquibaseModelProvider() throws DatabaseException, InvalidExampleException, SQLException {
104
105
106 DatabaseSnapshot snapshot = databaseSnapshot();
107
108 log.info("Creating LiquibaseModelProvider");
109
110
111 long start = System.currentTimeMillis();
112
113
114 String dbVendor = SpringUtils.getProperty(env, DB_VENDOR_KEY);
115 SequenceFinder finder = sequenceFinderMap().get(dbVendor);
116
117 if(finder == null) {
118 log.warn("NO MATCHING IMPLENTATION FOR SequenceFinder INTERFACE FOUND FOR VENDOR " + dbVendor);
119 }
120
121 LiquibaseSchemaProvider modelProvider = new LiquibaseSchemaProvider(snapshot, finder);
122
123 log.info("LiquibaseModelProvider created - Time: {}", FormatUtils.getTime(System.currentTimeMillis() - start));
124
125
126
127
128 databaseSnapshot().getDatabase().getConnection().close();
129
130 return modelProvider;
131 }
132
133 @Bean
134 public Schema schema() throws SQLException, DatabaseException, InvalidExampleException {
135 return liquibaseModelProvider().getSchema();
136 }
137
138 @Bean
139 public OracleSequenceFinder oracleSequenceFinder() throws SQLException {
140 DatabaseProcessContext context = dataSourceConfig.jdbcDatabaseProcessContext();
141 Connection conn = dataSourceConfig.jdbcDataSource().getConnection();
142
143 return new OracleSequenceFinder(conn, context.getUsername());
144 }
145
146 @Bean
147 public MySqlSequenceFinder mysqlSequenceFinder() {
148 return new MySqlSequenceFinder();
149 }
150 }