-
Notifications
You must be signed in to change notification settings - Fork 1.8k
/
CreateSequenceGenerator.java
145 lines (124 loc) · 7.17 KB
/
CreateSequenceGenerator.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
package liquibase.sqlgenerator.core;
import liquibase.database.Database;
import liquibase.database.core.*;
import liquibase.exception.DatabaseException;
import liquibase.exception.ValidationErrors;
import liquibase.sql.Sql;
import liquibase.sql.UnparsedSql;
import liquibase.sqlgenerator.SqlGeneratorChain;
import liquibase.statement.core.CreateSequenceStatement;
import liquibase.structure.core.Sequence;
import java.math.BigInteger;
public class CreateSequenceGenerator extends AbstractSqlGenerator<CreateSequenceStatement> {
@Override
public boolean supports(CreateSequenceStatement statement, Database database) {
return database.supportsSequences();
}
@Override
public ValidationErrors validate(CreateSequenceStatement statement, Database database, SqlGeneratorChain sqlGeneratorChain) {
ValidationErrors validationErrors = new ValidationErrors();
validationErrors.checkRequiredField("sequenceName", statement.getSequenceName());
validationErrors.checkDisallowedField("startValue", statement.getStartValue(), database, FirebirdDatabase.class);
validationErrors.checkDisallowedField("incrementBy", statement.getIncrementBy(), database, FirebirdDatabase.class);
if (isH2WithMinMaxSupport(database)) {
validationErrors.checkDisallowedField("minValue", statement.getMinValue(), database, FirebirdDatabase.class, HsqlDatabase.class);
validationErrors.checkDisallowedField("maxValue", statement.getMaxValue(), database, FirebirdDatabase.class, HsqlDatabase.class);
} else {
validationErrors.checkDisallowedField("minValue", statement.getMinValue(), database, FirebirdDatabase.class, H2Database.class, HsqlDatabase.class);
validationErrors.checkDisallowedField("maxValue", statement.getMaxValue(), database, FirebirdDatabase.class, H2Database.class, HsqlDatabase.class);
}
if (isPostgreWithoutAsDatatypeSupport(database)) {
validationErrors.checkDisallowedField("AS", statement.getDataType(), database, PostgresDatabase.class);
}
validationErrors.checkDisallowedField("ordered", statement.getOrdered(), database, HsqlDatabase.class, PostgresDatabase.class, MSSQLDatabase.class);
validationErrors.checkDisallowedField("dataType", statement.getDataType(), database, DB2Database.class, HsqlDatabase.class, OracleDatabase.class, MySQLDatabase.class, MSSQLDatabase.class, CockroachDatabase.class);
if (database instanceof H2Database && statement.getDataType() != null && !statement.getDataType().equalsIgnoreCase("bigint")) {
validationErrors.addWarning("H2 only creates BIGINT sequences. Ignoring requested type "+statement.getDataType());
}
return validationErrors;
}
@Override
public Sql[] generateSql(CreateSequenceStatement statement, Database database, SqlGeneratorChain sqlGeneratorChain) {
StringBuilder queryStringBuilder = new StringBuilder();
queryStringBuilder.append("CREATE SEQUENCE ");
if (database instanceof PostgresDatabase) {
// supported only for version >= 9.5 https://www.postgresql.org/docs/9.5/sql-createsequence.html
try {
if (database.getDatabaseMajorVersion() > 9
|| (database.getDatabaseMajorVersion() == 9 && database.getDatabaseMinorVersion() >= 5)) {
queryStringBuilder.append(" IF NOT EXISTS ");
}
} catch (DatabaseException e) {
// we can not determinate the PostgreSQL version so we do not add this statement
}
}
queryStringBuilder.append(database.escapeSequenceName(statement.getCatalogName(), statement.getSchemaName(), statement.getSequenceName()));
if (database instanceof HsqlDatabase || database instanceof Db2zDatabase) {
queryStringBuilder.append(" AS BIGINT ");
} else if (statement.getDataType() != null) {
if (!(database instanceof H2Database || database instanceof CockroachDatabase)) {
queryStringBuilder.append(" AS " + statement.getDataType());
}
}
if (!(database instanceof MariaDBDatabase) && !(database instanceof CockroachDatabase) && statement.getStartValue() != null) {
queryStringBuilder.append(" START WITH ").append(statement.getStartValue());
}
if (statement.getIncrementBy() != null) {
queryStringBuilder.append(" INCREMENT BY ").append(statement.getIncrementBy());
}
if (statement.getMinValue() != null) {
queryStringBuilder.append(" MINVALUE ").append(statement.getMinValue());
}
if (statement.getMaxValue() != null) {
queryStringBuilder.append(" MAXVALUE ").append(statement.getMaxValue());
}
if (database instanceof MariaDBDatabase && statement.getStartValue() != null) {
queryStringBuilder.append(" START WITH ").append(statement.getStartValue());
}
if (statement.getCacheSize() != null) {
if (database instanceof OracleDatabase || database instanceof Db2zDatabase || database instanceof PostgresDatabase || database instanceof MariaDBDatabase) {
if (BigInteger.ZERO.equals(statement.getCacheSize())) {
if (database instanceof OracleDatabase) {
queryStringBuilder.append(" NOCACHE ");
} else if (database instanceof MariaDBDatabase) {
queryStringBuilder.append(" CACHE 0");
}
} else {
queryStringBuilder.append(" CACHE ").append(statement.getCacheSize());
}
}
}
if (!(database instanceof MariaDBDatabase) && statement.getOrdered() != null) {
if (!(database instanceof SybaseASADatabase)) {
if (statement.getOrdered()) {
queryStringBuilder.append(" ORDER");
} else {
if (database instanceof OracleDatabase) {
queryStringBuilder.append(" NOORDER");
}
}
}
}
if (statement.getCycle() != null) {
if (statement.getCycle()) {
queryStringBuilder.append(" CYCLE");
}
}
return new Sql[]{new UnparsedSql(queryStringBuilder.toString(), getAffectedSequence(statement))};
}
protected Sequence getAffectedSequence(CreateSequenceStatement statement) {
return new Sequence().setName(statement.getSequenceName()).setSchema(statement.getCatalogName(), statement.getSchemaName());
}
private boolean isH2WithMinMaxSupport(Database database) {
return H2Database.class.isAssignableFrom(database.getClass())
&& ((H2Database) database).supportsMinMaxForSequences();
}
private boolean isPostgreWithoutAsDatatypeSupport(Database database) {
try {
return database instanceof PostgresDatabase && database.getDatabaseMajorVersion() < 10;
} catch (DatabaseException e) {
// we can't determinate the PostgreSQL version so we shouldn't throw validation error as it might work for this DB
return false;
}
}
}