我遇到某些代码问题,根本原因是会话级别的NLS_NUMERIC_CHARACTERS设置。
直接在数据库上运行查询时:
SQL> select 'nls_database_parameters' , p.* from nls_database_parameters p where PARAMETER = 'NLS_NUMERIC_CHARACTERS'
2 union all
3 select 'nls_session_parameters', p.* from nls_session_parameters p where PARAMETER = 'NLS_NUMERIC_CHARACTERS'
4 union all
5 select 'nls_instance_parameters', p.* from nls_instance_parameters p where PARAMETER = 'NLS_NUMERIC_CHARACTERS';
'NLS_DATABASE_PARAMETERS' PARAMETER VALUE
------------------------- ------------------------ -----
nls_database_parameters NLS_NUMERIC_CHARACTERS .,
nls_session_parameters NLS_NUMERIC_CHARACTERS .,
nls_instance_parameters NLS_NUMERIC_CHARACTERS .,
但是,当我从weblogic数据源
运行相同的查询时select 'nls_database_parameters' , p.* from nls_database_parameters p where PARAMETER = 'NLS_NUMERIC_CHARACTERS'
union all
select 'nls_session_parameters', p.* from nls_session_parameters p where PARAMETER = 'NLS_NUMERIC_CHARACTERS'
union all
select 'nls_instance_parameters', p.* from nls_instance_parameters p where PARAMETER = 'NLS_NUMERIC_CHARACTERS';
-- 'NLS_DATABASE_PARAMETERS', PARAMETER, VALUE
1 nls_database_parameters NLS_NUMERIC_CHARACTERS .,
2 nls_session_parameters NLS_NUMERIC_CHARACTERS ,
3 nls_instance_parameters NLS_NUMERIC_CHARACTERS .,
会话值错误,并且在通过weblogic数据源访问时被某些触发器/脚本重置,我检查了weblogic启动脚本等,看看我们是否在某处重置但没有帮助。
如果有人遇到类似的问题,那么这方面的任何指示/想法都会受到高度赞赏。
答案 0 :(得分:3)
不太可能明确设置。我谨慎地假设它是由于用于初始化JVM的user.language
和user.country
值而隐式设置的。我不确切知道WebLogic在默认情况下如何获取这些内容,但我猜测服务器的语言环境设置为逗号为小数分隔符的语言环境。
您应该可以通过在startWebLogic脚本中设置语言和国家/地区来覆盖默认的WebLogic设置
set JAVA_OPTIONS=%JAVA_OPTIONS% -Duser.language=en -Duser.country=US
当然,这可能会对其他事情产生影响(例如错误信息的语言)。
答案 1 :(得分:2)
我对Weblogic方面并不熟悉,但您可以通过在DBA_SOURCE中搜索其源代码对象(触发器,过程,包,函数)来从Oracle内部挖掘材料。它可能包含“execute immediate”语句(或等效的DBMS_SQL动态SQL调用),类似于:
alter session set nls_numeric_characters = ',.';
或者它也可以调用DBMS_SESSION.SET_NLS过程:
dbms_session.set_nls('NLS_NUMERIC_CHARACTERS', '".,"');
如下查询它应该指向一些嫌疑人(也可能是一些误报)。您可以通过所有者过滤来改进它。
SELECT *
FROM dba_source s
WHERE (upper(s.text) LIKE '%SET\_NLS%' ESCAPE '\'
OR upper(s.text) LIKE '%NLS\_NUMERIC\_CHARACTERS%' ESCAPE '\')
AND owner != 'SYS';
动态视图V $ SQL可能有你的命令,如果它是一个匿名的PL / SQL块或脚本。
SELECT *
FROM v$sql s
WHERE (upper(s.sql_fulltext) LIKE '%SET\_NLS%' ESCAPE '\'
OR upper(s.sql_fulltext) LIKE '%NLS\_NUMERIC\_CHARACTERS%' ESCAPE '\')
AND s.parsing_schema_name = 'YOUR_DB_USER';
如果您已经发现导致错误的代码并且它已受到控制,您还可以通过使用以下语法在to_number(或to_char)中显式执行转换来修复转换:
SQL> select to_number('1.5', '999999D999', 'NLS_NUMERIC_CHARACTERS=,.'),
2 to_number('1.5', '999999D999', 'NLS_NUMERIC_CHARACTERS=.,')
3 from dual;
TO_NUMBER('1.5','999999D999',' TO_NUMBER('1.5','999999D999','
------------------------------ ------------------------------
15 1,5
通过这种方式,您可以免受nls会话的影响,但修复所有代码以使用它可能是不可行的。