, ,

KILL SESSION и DISCONNECT SESSION

среда, 22 июля 2009 г. 0 коммент.

Решил разобраться каким способом более “правильно” убивать сессию, и какую при этом получит ошибку клиент.

  с активной транзакцией без активной транзакции

ALTER SYSTEM KILL SESSION 'integer1, integer2';

Сессия помечается, как killed.

Ожидается активность от клиента. Если клиент проявляет активность, то ему возвращаются ошибки.


ORA-00028: your session has been killed
ORA-01012: not logged on

Сессия помечается, как killed.

Ожидается активность от клиента. Если клиент проявляет активность, то ему возвращаются ошибки.


ORA-00028: your session has been killed
ORA-01012: not logged on

ALTER SYSTEM KILL SESSION 'integer1, integer2' IMMEDIATE; Сессия убивается.
Если клиент проявляет активность, то ему возвращаются ошибки.

ORA-03113: end-of-file on communication channel
ORA-03114: not connected to ORACLE

Сессия убивается.
Если клиент проявляет активность, то ему возвращаются ошибки.

ORA-03113: end-of-file on communication channel
ORA-03114: not connected to ORACLE

ALTER SYSTEM DISCONNECT SESSION 'integer1, integer2' POST_TRANSACTION; Ожидается ответ пользователя. Клиент может продолжить работать в той сессии с той же транзакцией(продолжить изменять данные). Если клиент выполнит commit, то данные будут зафиксированы. После этого клиент будет отсоединен, сессия будет завершена.
Если клиент после этого проявит активность, то ему будут возращены ошибка.

ORA-03114: not connected to ORACLE

Сессия помечается, как killed.

Ожидается активность от клиента. Если клиент проявляет активность, то ему возвращаются ошибки.


ORA-00028: your session has been killed
ORA-01012: not logged on

ALTER SYSTEM DISCONNECT SESSION 'integer1, integer2' IMMEDIATE; Клиент будет отсоединен, сессия будет завершена.
Если клиент проявляет активность, то ему возвращаются ошибки.

ORA-03113: end-of-file on communication channel
ORA-03114: not connected to ORACLE

Клиент будет отсоединен, сессия будет завершена.
Если клиент проявляет активность, то ему возвращаются ошибки.

ORA-03113: end-of-file on communication channel
ORA-03114: not connected to ORACLE

ALTER SYSTEM DISCONNECT SESSION 'integer1, integer2' POST_TRANSACTION IMMEDIATE; Опция IMMEDIATE игнорируется. Ожидается ответ пользователя. Клиент может продолжить работать в той сессии с той же транзакцией(продолжить изменять данные). Если клиент выполнит commit, то данные будут зафиксированы. После этого клиент будет отсоединен.
Если клиент после этого проявит активность, то ему будут возращены ошибка.

ORA-03114: not connected to ORACLE
Клиент будет отсоединен, сессия будет завершена.
Если клиент проявляет активность, то ему возвращаются ошибки.

ORA-03113: end-of-file on communication channel
ORA-03114: not connected to ORACLE

Одним цветом выделены ячейки, когда результат команды одинаков.

Подробнее можно почитать здесь.SQL Statements: ALTER SESSION to ALTER SYSTEM, 3 of 3

Резюме: если надо быстро и надежно убить сессию, то для этого идеально подходит команда ALTER SYSTEM KILL SESSION 'integer1, integer2' IMMEDIATE;



Читать полностью

, , ,

Номер дня недели

понедельник, 6 июля 2009 г. 2 коммент.

Достаточно часто необходимо получить номер дня в недели. Для этого обычно пользуемся функцией to_char и маской 'D'. Но возращаемое значение зависит от территории, а не от языка и поэтому часто возращается не правильное значение (обычно день недели, как принято в США). Если есть возможность, то можно установить территорию перед вызовом функции.


alter session set nls_territory = 'CIS';

Но тогда, нужно предварильно сохранить территорию, поменять, применить функцию, и востановить. Я пошел другим путем, создал свою функцию, которая считает день недели, от заданного дня.

create or replace function day_of_week(pd in date)
return integer
is
--monday
vd_start date := to_date('01.01.2001','dd.mm.yyyy');
vi_result integer;
begin
vi_result := mod(trunc(pd) - vd_start, 7);
if (vi_result >= 0) then
vi_result := vi_result + 1;
else
vi_result := vi_result + 8;
end if;

return(vi_result);
end day_of_week;

Теперь проверим.


SQL> alter session set nls_territory = 'CIS';

Session altered

SQL>
SQL> with t as
2 (
3 select to_date('08.06.2000','dd.mm.yyyy') as d from dual
4 union all
5 select to_date('01.01.2001','dd.mm.yyyy') as d from dual
6 union all
7 select trunc(sysdate) + 1 as d from dual
8 )
9 select t.d, to_char(t.d, 'dy', 'NLS_DATE_LANGUAGE = RUSSIAN') as d_day, to_char(t.d, 'd') as d_st, day_of_week(t.d) as d_fn
10 from t;

D D_DAY D_ST D_FN
----------- ----- ---- ----------
08.06.2000 чт 4 4
01.01.2001 пн 1 1
07.07.2009 вт 2 2

SQL> alter session set nls_territory = 'AMERICA';

Session altered

SQL>
SQL> with t as
2 (
3 select to_date('08.06.2000','dd.mm.yyyy') as d from dual
4 union all
5 select to_date('01.01.2001','dd.mm.yyyy') as d from dual
6 union all
7 select trunc(sysdate) + 1 as d from dual
8 )
9 select t.d, to_char(t.d, 'dy', 'NLS_DATE_LANGUAGE = RUSSIAN') as d_day, to_char(t.d, 'd') as d_st, day_of_week(t.d) as d_fn
10 from t;

D D_DAY D_ST D_FN
----------- ----- ---- ----------
08.06.2000 чт 5 4
01.01.2001 пн 2 1
07.07.2009 вт 3 2


Результат функции от смены территории, не меняется.

Читать полностью

,

Пребразование long в varchar2

четверг, 2 июля 2009 г. 0 коммент.

Понадобилось поработать с метаданными, часть полей еще имеют тип long.
Для использования типа long пришлось написать функцию, которая преобразовывает long в varchar2. Возращаеются только первые 4000 символов.


create or replace function long_to_varchar(ps_sql in varchar2
) return varchar2
is
vs_into varchar2(32000);
begin
execute immediate ps_sql
into vs_into;

return substr(vs_into, 1, 4000);
end long_to_varchar;

Пример использования:

select table_name,
index_name,
column_position,
replace(long_to_varchar( 'select column_expression from all_ind_expressions where index_owner=''' || index_owner || ''' and index_name=''' || index_name || ''''), '"')
from all_ind_expressions;


Читать полностью