001package ca.uhn.fhir.jpa.migrate.taskdef; 002 003/*- 004 * #%L 005 * HAPI FHIR Server - SQL Migration 006 * %% 007 * Copyright (C) 2014 - 2022 Smile CDR, Inc. 008 * %% 009 * Licensed under the Apache License, Version 2.0 (the "License"); 010 * you may not use this file except in compliance with the License. 011 * You may obtain a copy of the License at 012 * 013 * http://www.apache.org/licenses/LICENSE-2.0 014 * 015 * Unless required by applicable law or agreed to in writing, software 016 * distributed under the License is distributed on an "AS IS" BASIS, 017 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 018 * See the License for the specific language governing permissions and 019 * limitations under the License. 020 * #L% 021 */ 022 023import ca.uhn.fhir.i18n.Msg; 024import ca.uhn.fhir.jpa.migrate.JdbcUtils; 025import org.apache.commons.lang3.Validate; 026import org.apache.commons.lang3.builder.EqualsBuilder; 027import org.apache.commons.lang3.builder.HashCodeBuilder; 028import org.slf4j.Logger; 029import org.slf4j.LoggerFactory; 030 031import java.sql.SQLException; 032import java.util.Set; 033import java.util.stream.Collectors; 034 035import static org.apache.commons.lang3.StringUtils.isNotBlank; 036 037public class AddIdGeneratorTask extends BaseTask { 038 039 private static final Logger ourLog = LoggerFactory.getLogger(AddIdGeneratorTask.class); 040 private final String myGeneratorName; 041 042 public AddIdGeneratorTask(String theProductVersion, String theSchemaVersion, String theGeneratorName) { 043 super(theProductVersion, theSchemaVersion); 044 myGeneratorName = theGeneratorName; 045 } 046 047 @Override 048 public void validate() { 049 Validate.notBlank(myGeneratorName); 050 setDescription("Add id generator " + myGeneratorName); 051 } 052 053 @Override 054 public void doExecute() throws SQLException { 055 Set<String> tableNames = JdbcUtils.getTableNames(getConnectionProperties()); 056 String sql = null; 057 058 switch (getDriverType()) { 059 case MARIADB_10_1: 060 case MYSQL_5_7: 061 // These require a separate table 062 if (!tableNames.contains(myGeneratorName)) { 063 064 String creationSql = "create table " + myGeneratorName + " ( next_val bigint ) engine=InnoDB"; 065 executeSql(myGeneratorName, creationSql); 066 067 String initSql = "insert into " + myGeneratorName + " values ( 1 )"; 068 executeSql(myGeneratorName, initSql); 069 070 } 071 break; 072 case DERBY_EMBEDDED: 073 case H2_EMBEDDED: 074 sql = "create sequence " + myGeneratorName + " start with 1 increment by 50"; 075 break; 076 case POSTGRES_9_4: 077 sql = "create sequence " + myGeneratorName + " start 1 increment 50"; 078 break; 079 case ORACLE_12C: 080 sql = "create sequence " + myGeneratorName + " start with 1 increment by 50"; 081 break; 082 case MSSQL_2012: 083 sql = "create sequence " + myGeneratorName + " start with 1 increment by 50"; 084 break; 085 default: 086 throw new IllegalStateException(Msg.code(63)); 087 } 088 089 if (isNotBlank(sql)) { 090 Set<String> sequenceNames = 091 JdbcUtils.getSequenceNames(getConnectionProperties()) 092 .stream() 093 .map(String::toLowerCase) 094 .collect(Collectors.toSet()); 095 ourLog.debug("Currently have sequences: {}", sequenceNames); 096 if (sequenceNames.contains(myGeneratorName.toLowerCase())) { 097 logInfo(ourLog, "Sequence {} already exists - No action performed", myGeneratorName); 098 return; 099 } 100 101 executeSql(myGeneratorName, sql); 102 } 103 104 } 105 106 @Override 107 protected void generateEquals(EqualsBuilder theBuilder, BaseTask theOtherObject) { 108 AddIdGeneratorTask otherObject = (AddIdGeneratorTask) theOtherObject; 109 theBuilder.append(myGeneratorName, otherObject.myGeneratorName); 110 } 111 112 @Override 113 protected void generateHashCode(HashCodeBuilder theBuilder) { 114 theBuilder.append(myGeneratorName); 115 } 116}