powered by simpleCommunicator - 2.0.51     © 2025 Programmizd 02
Форумы / Oracle [игнор отключен] [закрыт для гостей] / Версия Оракла как number
11 сообщений из 11, страница 1 из 1
Версия Оракла как number
    #39997794
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Столкнулся с ограничением функции to_number(), которая вылетает если после цифр в номере содержатся буквы.

Задача элементарная, получить номер (число, не текст) версии Оракла в котором исполняется запрос.

Код: plaintext
DBMS_DB_VERSION.version
и
Код: plaintext
DBMS_DB_VERSION.release
содержат целую (11) и дробную (2) части версии, но эти значения недоступны из SQL, только из PL/SQL.

V$VERSION не очень полезен, текст вперемешку с числами: "CORE 11.2.0.1.0 Production"
Парсить исходя из одном-двух примеров негодно: сегодня он разделен табами, завтра может быть русифицирован с пробелами.

Остается встроенная таблица PRODUCT_COMPONENT_VERSION:
Код: plaintext
1.
2.
3.
4.
5.
   	PRODUCT	VERSION	STATUS
1	NLSRTL 	11.2.0.1.0	Production
2	Oracle Database 11g Enterprise Edition 	11.2.0.1.0	64bit Production
3	PL/SQL 	11.2.0.1.0	Production
4	TNS for 64-bit Windows: 	11.2.0.1.0	Production

Код: plsql
1.
select to_number( t.version ) from PRODUCT_COMPONENT_VERSION t where upper(t.product) like 'PL/SQL%'


Ошибка ORA-01722: invalid number, т.к. в числе лишние точки.

Код: plsql
1.
select to_number( regexp_substr( t.version, '^\d+\.*\d*' ) ) from PRODUCT_COMPONENT_VERSION t where upper(t.product) like 'PL/SQL%';



Работает, но наверное есть что-то попроще. Во втором параметре to_number() возможно как-то сказать чтоб игнорились лишние символы после числа? Я не нашел такого.
...
Рейтинг: 0 / 0
Версия Оракла как number
    #39997795
Фотография Elic
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL
to_number(), которая вылетает если после цифр в номере содержатся буквы.
Надо же, какой прям-таки подленький нежданьчик.
...
Рейтинг: 0 / 0
Версия Оракла как number
    #39997806
Правильный Вася
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Есть ещё такой интересный нюанс, как параметр COMPATIBLE. Он может не совпадать с версией ПО, но заставлять БД работать в режиме совместимости с указанной версией.

Проверяется как
Код: plsql
1.
SELECT * FROM V$system_parameter WHERE NAME = 'compatible'


И там нет лишних букв :)
...
Рейтинг: 0 / 0
Версия Оракла как number
    #39997826
Фотография SY
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL

Задача элементарная, получить номер (число, не текст) версии Оракла в котором исполняется запрос.


Медитируй на тему число и числовая строка. А так:

Код: plsql
1.
SELECT VERSION FROM V$INSTANCE;



SY.
...
Рейтинг: 0 / 0
Версия Оракла как number
    #39997827
Фотография SY
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL


Код: plaintext
DBMS_DB_VERSION.version
и
Код: plaintext
DBMS_DB_VERSION.release
содержат целую (11) и дробную (2) части версии, но эти значения недоступны из SQL, только из PL/SQL.


доступны:

Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
with function f_ver
       return number
       is
       begin
           return dbms_db_version.version;
       end;
     function f_rel
       return number
       is
       begin
           return dbms_db_version.release;
       end;
select  f_ver,
        f_rel
  from  dual
/

     F_VER      F_REL
---------- ----------
        12          2

SQL>



SY.
...
Рейтинг: 0 / 0
Версия Оракла как number
    #39997882
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
SY,

спасибо за отличный пример с этими инлайн функциями, я совсем про них забыл ввиду недоступности в 11м оракле.
В принципе, я могу их сделать и глобальными, если будут использоваться в нескольких местах.

Я посмотрел как другие справляются с поведением to_number(), которое строго требует точного формата.
Есть несколько решений, среди них:
- "DEFAULT ON CONVERSION ERROR", тоже фишка появилась в 12.0
- regexp_substr - отмывание чисел после которых идет текст
- написание более спокойной функции, которая выдает null вместо исключений

Один DBA так и поступил, взято отсюда: http://oracle.ehelp365.com/oracle-to_number

Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
CREATE FUNCTION get_only_numbers (P_TEXT VARCHAR2)
 RETURN NUMBER
IS
BEGIN
  RETURN TO_NUMBER(P_TEXT);
 
EXCEPTION when VALUE_ERROR
          then RETURN null;
END get_only_numbers;
...
Рейтинг: 0 / 0
Версия Оракла как number
    #39997907
Фотография Sayan Malakshinov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Модератор форума
НеофитSQL,

В чем, собственно, смысл, если важно 4е число, особенно в случае 12.1.0.1/12.1.0.2?
...
Рейтинг: 0 / 0
Версия Оракла как number
    #39997909
Фотография SY
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL,

Ну и причем тут поведение to_number()??? У тебя конкретная задача получить версию и релиз. Версия это строка следующего формата:




This is a text description of admin002.gif. The figure displays a release number and notes the significance of each digit. The release number is 11.2.0.1.0.

The significance of each number (reading from left to right) is as follows:

11 is the major database release number

2 is the database maintenence release number

0 is the application server release number

1 is the component-specific release number

0 is the platform-specific release number

End of image description.


Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
select  to_number(regexp_substr(version,'\d+',1,1)) major_release,
        to_number(regexp_substr(version,'\d+',1,2)) maintenance_release,
        to_number(regexp_substr(version,'\d+',1,3)) application_server_release,
        to_number(regexp_substr(version,'\d+',1,4)) component_specific_release,
        to_number(regexp_substr(version,'\d+',1,5)) platform_specific_release
  from  product_component_version
  where product = 'PL/SQL '
/

MAJOR_RELEASE MAINTENANCE_RELEASE APPLICATION_SERVER_RELEASE COMPONENT_SPECIFIC_RELEASE PLATFORM_SPECIFIC_RELEASE
------------- ------------------- -------------------------- -------------------------- -------------------------
           12                   2                          0                          1                         0

SQL>



SY.
...
Рейтинг: 0 / 0
Версия Оракла как number
    #39997957
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
SY,

Так еще лучше. Меня интересовали первые два числа версии, поэтому собирался прочитать его как десятичную дробь, благо есть удобная функция to_number() которая это умеет. Третий параметр regexp_substr - это для меня новая штука, выглядит очень удобно.

Вопрос по поводу
Код: plsql
1.
where product = 'PL/SQL '



с пробелом: у меня в 11.2 тоже пробел, хотя Оракл не предоставляет никаких гарантий по инвариантности этой строки. В моем примере я подстраховался и использовал
Код: plsql
1.
where upper(t.product) like 'PL/SQL%'

, хотя trim() было бы лучше.

Почитав еще документацию производителя ( https://docs.oracle.com/cd/E18283_01/appdev.112/e16760/d_dbver.htm) и примеры использования, я убедился что рекомендуемый способ проверки соответствия версии это через встроенный пакет DBMS_DB_VERSION.

Если в будущем процессе миграции на новый оракл мне потребуется различать между версиями, я буду знать как это делать.
...
Рейтинг: 0 / 0
Версия Оракла как number
    #39997966
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Мои вопросы в этой теме отвечены, подытожу:

Документация оракла рекомендует использовать пакет констант DBMS_DB_VERSION, который содержит номера версии в виде целых чисел, удобных для использования в PL/SQL. Там же приводятся примеры использования.

https://docs.oracle.com/cd/E18283_01/appdev.112/e16760/d_dbver.htm

При необходимости доступиться к этим числам из запроса, можно обернуть интересующие значения как глобальные функции, или, начиная с Оракла 12, как инлайн функции - примеры есть в этой теме (Спасибо, SY).

Мой второй вопрос был как научить to_number() читать строчки с лишней информацией не вылетая по исключению.
Поведение этой функции через малодокументируемый второй параметр изменить нельзя, и требуется предварительная чистка строки ввода.
Среди тех, кто решал эту задачу до меня и рассказал на интернете, канонического решения не наблюдается.
Кто-то чистит через regex_substr(), кто-то написал безопасную версию функции - все рабочие варианты.
Например условия в C/C++:
Код: plaintext
1.
2.
// убедиться что unicast
if( strtoul(strIPv4,10,NULL) < 224 )



в PL/SQL можно написать так:
Код: plsql
1.
if to_number(nvl(regexp_substr(strIPv4,'^\d+'),'0')) < 224 then 
...
Рейтинг: 0 / 0
Версия Оракла как number
    #39997969
Dimitry Sibiryakov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQLЕсли в будущем процессе миграции на новый оракл мне потребуется различать между версиями

Обычно это не требуется. Просто пишешь нужную версию в системных требованиях твоего поделия.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
11 сообщений из 11, страница 1 из 1
Форумы / Oracle [игнор отключен] [закрыт для гостей] / Версия Оракла как number
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]