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_6382_test.py

73 lines
2.6 KiB
Python

#coding:utf-8
"""
ID: issue-6621
ISSUE: 6621
TITLE: Triggers accessing a table prevent concurrent DDL command from dropping that table
DESCRIPTION:
Test creates two tables which are linked by master-detail relationship.
We add one record into the main table and then update it with issuing further COMMIT.
After this we try to DROP this table in another connect.
If this connect started WAIT transaction (i.e. without lock timeout) then it can hang forever if case of
regression of this fix. Because of this, we change its waiting mode by adding lock_timeout parameter to
TPB and set it to 1 second.
BEFORE fix this lead to:
DatabaseError: / Error while commiting transaction: / - SQLCODE: -901
- lock time-out on wait transaction / - unsuccessful metadata update
- object TABLE "T_DETL" is in use / -901 / 335544510
AFTER fix this DROP TABLE statement must pass without any error.
JIRA: CORE-6382
FBTEST: bugs.core_6382
"""
import pytest
from firebird.qa import *
from firebird.driver import tpb, Isolation
init_script = """
recreate table t_detl(id int primary key using index t_detl_pk, pid int);
recreate table t_main(id int primary key using index t_main_pk);
alter table t_detl add constraint t_detl_fk foreign key(pid) references t_main(id) on update cascade using index t_detl_fk;
commit;
insert into t_main values(123);
commit;
"""
db = db_factory(init=init_script)
act = python_act('db')
expected_stdout = """
None
Passed.
"""
@pytest.mark.version('>=4.0')
def test_1(act: Action, capsys):
# # NB: adding this timeout does NOT change WAIT-nature of transaction as it is considered by engine.
# # (in other words: such transaction will not became 'no wait' which must not be used in this test):
custom_tpb = tpb(isolation=Isolation.SNAPSHOT, lock_timeout=5)
#
with act.db.connect() as con1, act.db.connect() as con2:
con1.main_transaction.default_tpb = custom_tpb
con2.main_transaction.default_tpb = custom_tpb
#
con1.execute_immediate('update t_main set id=-id')
con1.commit()
con2.execute_immediate('drop table t_detl')
con2.commit()
cur = con2.cursor()
cur.execute("select r.rdb$relation_name from rdb$database d left join rdb$relations r on r.rdb$relation_name = upper('t_detl')")
for r in cur:
print(r[0])
print('Passed.')
# Check
act.expected_stdout = expected_stdout
act.stdout = capsys.readouterr().out
assert act.clean_stdout == act.clean_expected_stdout