Вести с полей. День проблем с серверами
Привет всем.
Сегодня интересный день. День багов. Все началось с того, что я решил обновить основной тестовый сервер до FB2.5.1.26182. На нем перестал отрабатывать один из служебных запросов провайдера.
Выглядит этот запрос так:
select pk_c.rdb$relation_name as pk_table_name,
iseg_pk.rdb$field_name as pk_field_name,
fk_c.rdb$relation_name as fk_table_name,
iseg_fk.rdb$field_name as fk_field_name,
rc.rdb$const_name_uq as pk_name,
rc.rdb$constraint_name as fk_name,
rc.rdb$update_rule as update_rule,
rc.rdb$delete_rule as delete_rule,
iseg_fk.rdb$field_position as field_position
from rdb$index_segments iseg_pk
join rdb$relation_constraints pk_c
join rdb$ref_constraints rc
join rdb$relation_constraints fk_c
join rdb$index_segments iseg_fk
on fk_c.rdb$index_name=iseg_fk.rdb$index_name and
iseg_fk.rdb$field_position=iseg_pk.rdb$field_position
on rc.rdb$constraint_name=fk_c.rdb$constraint_name
on pk_c.rdb$constraint_name=rc.rdb$const_name_uq
on iseg_pk.rdb$index_name = pk_c.rdb$index_name
Сервер возвращает ошибку
Dynamic SQL Error.
SQL error code = -206.
Column unknown.
ISEG_PK.RDB$FIELD_POSITION.
At line 16, column 49.
После непродолжительной консультации по этой теме, было принято решение на всякий случай переделать сам запрос, а не ждать исправления в сервере. Если такое вообще будет.
Решив проблему с FB, подумалось об IB — с ним там вообще как? Все в порядке?
Для получения ответа на этот риторический вопрос был запущен тест schema.002.read_schema.schema_cache_0. Это адский тест, который перебирает все возможные комбинации получения схем метаданных при выключенном кэше. Адский, потому что было время, когда он работал больше суток. Сейчас, после многочисленных оптимизаций в провайдере — где-то в районе 3.5 часов.
Сервер — IB10. Получили такие ошибки:
[23.01.2011 18:49:52] ERROR: [read_schema] Schema DBSCHEMA_CONSTRAINT_COLUMN_USAGE [{C8B52216-5CF3-11CE-ADE5-00AA0044773D}]
GetSchema return BAD rowset with 0 records for this restrictions:
«CONSTRAINT_NAME»=bstr»CHECK_DUAL»[23.01.2011 19:02:21] ERROR: [read_schema] Schema DBSCHEMA_CONSTRAINT_TABLE_USAGE [{C8B52217-5CF3-11CE-ADE5-00AA0044773D}]
GetSchema return BAD rowset with 0 records for this restrictions:
«CONSTRAINT_NAME»=bstr»CHECK_DUAL»[23.01.2011 19:13:30] ERROR: [read_schema] Schema DBSCHEMA_COLUMN_PRIVILEGES [{C8B52221-5CF3-11CE-ADE5-00AA0044773D}]
GetSchema return BAD rowset with 0 records for this restrictions:
«COLUMN_NAME»=bstr»CHAR_OCTETS»
Ага. Давайте рассмотрим поближе первую ошибку. Для этого был создан изолированный тест на VBS
option explicit
dim cn
set cn=createobject("ADODB.Connection")
cn.Provider="LCPI.IBProvider"
cn.Properties("location") ="vxpsp2-ib100:e:\database\ibp_test_ib100_d3.gdb"
cn.Properties("user id") ="gamer"
cn.Properties("password") ="vermut"
cn.Properties("ctype") ="win1251"
cn.Properties("dbclient_library") ="d:\Users\Dima\IB_FB_YA\IB100\gds32.dll"
cn.Properties("stmt_cache__time") =0
call cn.Open()
wscript.echo "DBMS Name :"&cstr_sn(cn.properties("DBMS Name").value)
wscript.echo "DBMS Version:"&cstr_sn(cn.properties("DBMS Version").value)
wscript.echo ""
call cn.BeginTrans()
test_1(cn)
test_2(cn)
call wscript.quit(0)
'+++++++++++++++++++++++++++++++++++++++++++
sub test_1(cn)
wscript.echo "------------------ TEST 1"
dim cmd
set cmd=create_cmd(cn)
call run_cmd(cmd,"INTEG_3")
set cmd=create_cmd(cn)
call run_cmd(cmd,"CHECK_DUAL")
end sub' test_1
'+++++++++++++++++++++++++++++++++++++++++++
sub test_2(cn)
wscript.echo "------------------ TEST 2"
dim cmd
set cmd=create_cmd(cn)
call run_cmd(cmd,"INTEG_3")
'set cmd=create_cmd(cn)
call run_cmd(cmd,"CHECK_DUAL")
end sub' test_2
'+++++++++++++++++++++++++++++++++++++++++++
private function create_cmd(cn)
dim cmd
set cmd=createobject("ADODB.Command")
cmd.ActiveConnection=cn
cmd.CommandText= _
"select rc1.rdb$constraint_name," & vbCrLf & _
"rc1.rdb$relation_name," & vbCrLf & _
"iseg1.rdb$field_name," & vbCrLf & _
"rc1.rdb$constraint_type" & vbCrLf & _
"from rdb$relation_constraints rc1" & vbCrLf & _
"join rdb$index_segments iseg1" & vbCrLf & _
"on rc1.rdb$index_name=iseg1.rdb$index_name" & vbCrLf & _
"where rc1.rdb$constraint_name=:a" & vbCrLf & _
"union" & vbCrLf & _
"select rc2.rdb$constraint_name," & vbCrLf & _
"dep2.rdb$depended_on_name," & vbCrLf & _
"dep2.rdb$field_name," & vbCrLf & _
"rc2.rdb$constraint_type" & vbCrLf & _
"from rdb$relation_constraints rc2" & vbCrLf & _
"join rdb$check_constraints cc2" & vbCrLf & _
"join rdb$dependencies dep2" & vbCrLf & _
"on dep2.rdb$dependent_name=cc2.rdb$trigger_name and" & vbCrLf & _
"dep2.rdb$dependent_type=2 and" & vbCrLf & _
"((dep2.rdb$depended_on_type is NULL) or" & vbCrLf & _
"(dep2.rdb$depended_on_type in (0,1))) and" & vbCrLf & _
"(dep2.rdb$field_name is not null) and" & vbCrLf & _
"(dep2.rdb$field_name<>'')" & vbCrLf & _
"on (rc2.rdb$constraint_name=cc2.rdb$constraint_name and" & vbCrLf & _
"rc2.rdb$constraint_type='CHECK')" & vbCrLf & _
"where rc2.rdb$constraint_name=:a" & vbCrLf & _
"union" & vbCrLf & _
"select rc3_fk.rdb$constraint_name," & vbCrLf & _
"rc3_pk.rdb$relation_name," & vbCrLf & _
"iseg3_pk.rdb$field_name," & vbCrLf & _
"rc3_fk.rdb$constraint_type" & vbCrLf & _
"from rdb$relation_constraints rc3_fk" & vbCrLf & _
"join rdb$ref_constraints ref_c3" & vbCrLf & _
"join rdb$relation_constraints rc3_pk" & vbCrLf & _
"join rdb$index_segments iseg3_pk" & vbCrLf & _
"on rc3_pk.rdb$index_name=iseg3_pk.rdb$index_name" & vbCrLf & _
"on ref_c3.rdb$const_name_uq=rc3_pk.rdb$constraint_name" & vbCrLf & _
"on rc3_fk.rdb$constraint_name=ref_c3.rdb$constraint_name" & vbCrLf & _
"where rc3_fk.rdb$constraint_name=:a"
set create_cmd=cmd
end function 'create_cmd
'+++++++++++++++++++++++++++++++++++++++++++
private sub run_cmd(cmd,param)
wscript.echo ""
wscript.echo "param:"¶m
cmd("a")=param
dim rs
set rs=cmd.execute()
while(not rs.eof)
wscript.echo cstr_sn(rs(0).value)
call rs.movenext()
wend
end sub 'run_cmd
'+++++++++++++++++++++++++++++++++++++++++++
Function cstr_sn(s)
If (IsNull(s)) Then
cstr_sn = "#NULL"
Else
cstr_sn = CStr(s)
End If
End Function ' su_cstr_sn_ex
'+++++++++++++++++++++++++++++++++++++++++++
Вывод
DBMS Name :InterBase
DBMS Version:10.0.0.247
—————— TEST 1
param:INTEG_3
INTEG_3
param:CHECK_DUAL
CHECK_DUAL
—————— TEST 2
param:INTEG_3
INTEG_3
param:CHECK_DUAL
Первый тест пересоздает запрос. Второй тест — дважды вызывает один и тот же запрос с разными параметрами. Результаты работы тестов должны быть идентичными. Однако во втором тесте, когда запрос выполняется второй раз, мы получаем пустое множество.
А что по этому поводу нам скажет IB7.5?
DBMS Name :InterBase
DBMS Version:7.5.1.80
—————— TEST 1
param:INTEG_3
INTEG_3
param:CHECK_DUAL
CHECK_DUAL
—————— TEST 2
param:INTEG_3
INTEG_3
param:CHECK_DUAL
CHECK_DUAL
Он (InterBase 7.5.1) говорит, что все путём. Оба теста возвращают идентичные результаты. Даже если разрешить пул запросов (закомментировать установку свойства stmt_cache__time) — результат будет тот же. То есть правильный.
Вот такие вот дела.
Interbase 2010 on 24 января, 2011
Interbase пошел по наклонной?