6
0
mirror of https://github.com/FirebirdSQL/firebird-qa.git synced 2025-01-22 21:43:06 +01:00
firebird-qa/tests/bugs/core_5110_test.py

108 lines
4.1 KiB
Python

#coding:utf-8
#
# id: bugs.core_5110
# title: False PK\FK violation could be reported when attachment used isc_dpb_no_garbage_collect flag
# decription:
# Fix relates only such transactions that are in the state 'dead', see: https://sourceforge.net/p/firebird/code/62965
# This mean that such Tx should did sufficiently big changes _before_ inserting key into table with PK/UK.
# Number of these changes should force Tx-1 be rolled back via TIP rather than undo+commit.
# Simple experiment shows that threshold is near 80'000 rows being inserted into the table with single
# text field of length = 50 characters. This test inserts 120'000 rows for ensuring that rollback will be
# done via TIP.
# ===
# ::: NB :::
# Minimal version of 'fdb' driver should be 1.5.1 for this test can be run.
# ::::::::::
# Confirmed exception with PK/UK violation on WI-V3.0.0.32332 (11-feb-2016), 2.5.6.26970 (05-feb-2016):
# - SQLCODE: -803 ; - violation of PRIMARY or UNIQUE KEY constraint "TEST_ID_UNQ" on table "TEST"
# - Problematic key value is ("ID" = 1) ; -803 ; 335544665
#
# No such error on WI-T4.0.0.32371, WI-V2.5.6.26979.
#
# tracker_id: CORE-5110
# min_versions: ['2.5.6']
# versions: 2.5.6
# qmid: None
import pytest
from firebird.qa import db_factory, python_act, Action
from firebird.driver import DbWriteMode, TPB, Isolation
# version: 2.5.6
# resources: None
substitutions_1 = []
init_script_1 = """
recreate table test( id int, who varchar(5), constraint test_id_unq unique(id) using index test_id_unq );
recreate table tbig( s varchar(50) );
"""
db_1 = db_factory(sql_dialect=3, init=init_script_1)
# test_script_1
#---
#
# import fdb
#
# db_conn.close()
#
# # This reduces test running time from ~5" to ~4":
# runProgram('gfix',[dsn,'-user',user_name,'-pas',user_password,'-w','async'])
#
# # Specifying 'no_gc=1' requires fdb version >= 1.5.1, issued 19-feb-2016, see:
# # http://sourceforge.net/p/firebird/code/62989
# conn = fdb.connect(dsn=dsn, user=user_name, password=user_password, no_gc=1)
#
# customTPB = ( [ fdb.isc_tpb_concurrency ] )
# tx1=conn.trans()
# tx2=conn.trans()
#
# tx1.begin( tpb=customTPB )
# tx2.begin( tpb=customTPB )
#
# cur1=tx1.cursor()
# cur2=tx2.cursor()
#
# print('Tx-1: insert big number of rows.')
# cur1.execute("insert into tbig(s) select rpad('', 50, uuid_to_char(gen_uuid())) from rdb$types,rdb$types,(select 1 k from rdb$types rows 2) rows 120000")
# cur1.execute("insert into test(id, who) values(1, 'Tx-1')")
# tx1.rollback()
# print('Tx-1: rollback via TIP.')
# cur2.execute("insert into test(id, who) values(1, 'Tx-2')")
# print('Tx-2: insert single test record.')
# tx2.rollback()
#
#---
act_1 = python_act('db_1', substitutions=substitutions_1)
expected_stdout_1 = """
Tx-1: insert big number of rows.
Tx-1: rollback via TIP.
Tx-2: insert single test record.
"""
@pytest.mark.version('>=2.5.6')
def test_1(act_1: Action):
with act_1.connect_server() as srv:
srv.database.set_write_mode(database=act_1.db.db_path, mode=DbWriteMode.ASYNC)
#
custom_tpb = TPB(isolation=Isolation.CONCURRENCY).get_buffer()
with act_1.db.connect(no_gc=True) as con:
tx1 = con.transaction_manager(custom_tpb)
tx2 = con.transaction_manager(custom_tpb)
tx1.begin()
tx2.begin()
cur1 = tx1.cursor()
cur2 = tx2.cursor()
# Test starts here, no exception should occur
# Tx-1: insert big number of rows.
cur1.execute("insert into tbig(s) select rpad('', 50, uuid_to_char(gen_uuid())) from rdb$types,rdb$types,(select 1 k from rdb$types rows 2) rows 120000")
cur1.execute("insert into test(id, who) values(1, 'Tx-1')")
# Tx-1: rollback via TIP.
tx1.rollback()
# Tx-2: insert single test record.
cur2.execute("insert into test(id, who) values(1, 'Tx-2')")
tx2.rollback()