現在のプロジェクトの移行ツールとしてliquibaseを使用しています。なぜliquibaseは常に独自のシーケンスを使用していますか?
問題は、エンティティの自動生成IDにカスタムシーケンスを使用しようとしていますが、何か問題が発生していることです。
私は下記の似たようエンティティテーブルとカスタムシーケンスを定義しました:
<databaseChangeLog>
<changeSet id="create_orders_table" author="I am">
<createTable tableName="ORDERS">
<column name="id" type="SERIAL" valueComputed="SEQ_ORDERS.NEXTVAL" valueSequenceCurrent="SEQ_ORDERS.CURRENT" valueSequenceNext="SEQ_ORDERS.NEXTVAL" defaultValueSequenceNext="SEQ_ORDERS.NEXTVAL">
<constraints primaryKey="true" unique="true"/>
</column>
<column name="number" type="VARCHAR(64)"/>
...
</createTable>
</changeSet>
<changeSet id="add_sequence" author="I am">
<createSequence sequenceName="SEQ_ORDERS" cycle="false" minValue="1" maxValue="9223372036854775807" startValue="1" incrementBy="1"/>
</changeSet>
</databaseChangeLog>
しかし、この移行が印加されたとき、私は、PostgreSQLで、次のテーブル構造を参照してください。
CREATE TABLE public.orders
(
id integer NOT NULL DEFAULT nextval('orders_id_seq'::regclass),
"number" character varying(64),
...
CONSTRAINT pk_orders PRIMARY KEY (id)
)
WITH (
OIDS=FALSE
);
まず、予測できません私のためのものはここに私のSEQ_ORDERS
の代わりに自分自身orders_id_seq
を書いた理由は何ですか?
次の私は、一般的なJPAコードを書いて、それが春を使用してテストだ:私が見るテストログで
@Entity(name = "ORDERS")
public class Order {
@Id
@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "ORDERS_ID_GEN")
@SequenceGenerator(name = "ORDERS_ID_GEN", sequenceName = "SEQ_ORDERS")
private long id;
private String number;
//... getters,setters and other stuff
}
public interface OrderRepository extends JpaRepository<Order,Long> {}
テスト
@RunWith(SpringRunner.class)
@DataJpaTest
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
@Rollback(value = false)
public class OrderRepositoryTest {
@Autowired
private TestEntityManager testEntityManager;
@Autowired
private OrderRepository orderRepository;
@Test
public void testThatIdsOfOrdersGenerateCorrectly(){
Order orderOne = new Order();
orderOne.setNumber("order-n-01");
Order orderTwo = new Order();
orderTwo.setNumber("order-n-02");
Order orderThree = new Order();
orderThree.setNumber("order-n-03");
testEntityManager.persist(orderOne);
testEntityManager.persist(orderTwo);
testEntityManager.persist(orderThree);
Assert.assertThat(orderRepository.findOne(new Long(1)),is(orderOne));
Assert.assertThat(orderRepository.findOne(new Long(2)),is(orderTwo));
Assert.assertThat(orderRepository.findOne(new Long(3)),is(orderThree));
}
}
:
Hibernate: select nextval ('seq_orders')
...
java.lang.AssertionError:
Expected: is <Order(id=50, number=order-n-01, ...>
but: was null
テストがで終了した後DB私はid = 50,51,52の3つの注文を見た。
初めて、私はorders_id_seq
が毎回50ずつ増分すると思った。 私がテストした後、そのままorders_id_seq
を見たときに非常にあわてた(現在値= 1)が、私のSEQ_ORDERSが、私はもう一度テストを実行すると、私は、IDS 100101102
でして次の3つの注文を得た。1.
に増分されました誰かがここで何が起こっているのか教えてください。 そして、liquibaseを作る方法& postgresqlは正しいことをしていますか?
私が使用しています:PostgreSQLの9.6(org.postgresql.9.4.1212 JDBCドライバ)、LiquiBaseを3.5.3、春ブーツ1.5.2
春Bootテスト設定:
spring.jpa.hibernate.ddl-auto=none
spring.jpa.generate-ddl=false
spring.jpa.database=postgresql
spring.datasource.initialize=false
spring.datasource.username=postgres
spring.datasource.password=********
spring.datasource.url=jdbc:postgresql://localhost:5432/ORDERS_TEST
spring.datasource.driver-class-name=org.postgresql.Driver
liquibase.change-log=classpath:/db/changelog/changelog-master.xml
うん、そのような変更履歴はPostgreSQLが私のシーケンスを使用しますが、私はとにかく50,51,52のIDを得ました。 – rvit34
@ rvit34:難読化レイヤのマッピングにおそらく何か問題があります - 私はHibernateを使用しないので、それを手伝ってはいけません)。別の質問をすることもできます(SOに関する質問には、1つの質問のみを含める必要があります)。しかし、Hibernateでは何らかのキャッシュのように思えます。あるいは、 'cache =" 50 "'でシーケンスを作成したでしょうか? –
PgAdminでわかるように、私のSEQ_ORDERSのキャッシュは1 – rvit34