Db character set, client character set, OS character set

Hi,
I'm confused about all these character set: DB character set, National character set, Client character set, Operating system character set, NLS_LANGUAGE parameter in init.ora file, NLS_LANG parameter in registry.
Can anyone explain the differences of these to me?
Many thanks.

Hi 101514,
The answers to your questions are listed here in the Globalization Support FAQ on OTN.
http://technet.oracle.com/tech/globalization/content.html
Regards
Nat

Similar Messages

  • UTL_MAIL shows character set in email client

    Hello,
    Database: Oracle Database 10g Enterprise Edition Release 10.1.0.3.0
    OS: Red Had Enterprise Linux (version 3)
    I'm trying to use the UTL_MAIL package to send an email and the actual mail sending works fine. However on the client side the database character set (WE8ISO8859P1) is displayed in the "From:" field and it's also displayed in the "Subject:" field (along with the actual email address/subject). Can someone please let me know why this is happening and how I fix it?
    The code I use is:
    <font face="Courier New" size="2">
    <font color = "maroon">exec</font> <font color = "maroon">utl_mail</font><font color = "silver">.</font><font color = "maroon">send</font><font color = "maroon">(</font> <font color = "maroon">sender</font> <font color = "silver">=&gt;</font> <font color = "red">'&quot;Database Check&quot; <[email protected]>'</font><font color = "silver">,</font>
    <font color = "maroon">recipients</font> <font color = "silver">=&gt;</font> <font color = "red">'&quot;Oracle DBA&quot; <[email protected]>'</font><font color = "silver">,</font> <font color = "maroon">
    <br>subject</font> <font color = "silver">=&gt;</font><font color = "red">'test email subject'</font><font color = "silver">,</font> <font color = "maroon">
    <br>message</font> <font color = "silver">=&gt;</font> <font color = "red">'message body text'</font><font color = "silver">,</font> <font color = "maroon">
    <br>mime_type</font> <font color = "silver">=&gt;</font><font color = "red">'text/plain charset=us-ascii;'</font><font color = "maroon">)</font><font color = "silver">;</font> 
    </font>
    Here's a screenshot of how the email appears on the client-side (Novell GroupWise. Outlook 2007 also displays it the same way). Please note I've blanked out the recipients name (which is displayed correctly, without the character set).
    http://oi53.tinypic.com/25usgme.jpg
    So why is the character set displayed? I've tried various combinations of using double-quotes and single quotes to no avail. Also the email is displayed perfectly fine if I use the old UTL_SMTP package!
    Please help!
    Thanks!
    Edited by: feersum_endjinn on 27-Jan-2011 03:00

    Can you post the raw e-mail received by the Groupwise/Outlook client? Please use the tag as prefix and suffix for the contents, in order to prevent the pre-formatted text from being formatted by Jives.                                                                                                                                                                                                                                                                                                                                                                                                                               

  • Client-side greek character set problem

    hi everyone,
    i am a .net developer and absolutelly new to oracle, its my first project that i have make oracle and .net co-operate and it's proving to be a nightmare!
    i ll try and provide as much info as possible to you
    we have a unix sap server with oracle 10.something on it (i can check exactly what version if that's of importance) and i am writting a .net app which accesses the oracle db and retrieve some data we need
    the locale settings of the db are american_america.we8dec and i cannot temper with that machine, it is out of the question
    i have made the connection to the db using just connection string info, not tns and stuff, and i have set my dev machine's nls_lang to we8dec everywhere i could find it with a 'find' in the registry
    however my app displays the data (which is in greek) showing random symbols that obviously make to sense
    furthermore when i connect to the db via sql developer or navicat i still get the same symbols
    i understand it is something to do with my client system's settings but i cant work it out
    i would really appreciate your help i am sorry if it is something very simple but i just cant find it
    thanks

    user9084006 wrote:
    i am a .net developer and absolutelly new to oracle, its my first project that i have make oracle and .net co-operate and it's proving to be a nightmare!Welcome. It's a brand new universe, but if you take it step by step I'm sure you'll do fine. Get someone near with Oracle dev and dba background to guide you, so you don't get stuck or go down broken roads.
    we have a unix sap server with oracle 10.something on it (i can check exactly what version if that's of importance)It is of importance most of the time. Down to at least 4 positions (for example, "10g" is just a marketing label and mostly useless in a techincal context - 10.2.0.5 is more like it).
    Also mention platform (unix OS) details.
    and i am writting a .net app which accesses the oracle db and retrieve some data we needHow is the to-be retrieved data loaded or entered to begin?
    >
    the locale settings of the db are american_america.we8dec and i cannot temper with that machine, it is out of the question Please post output from:
    SQL> select * from nls_database_parameters where parameter like '%CHARACTERSET';
    and i have set my dev machine's nls_lang to we8dec everywhere i could find it with a 'find' in the registryDoes your dev (client) machine use a "we8dec" character set? Likely, as you seem to be on Windows, you should have set nls_lang client char set part to match win-1252 or whatever client char set (code page) is in use.
    however my app displays the data (which is in greek) showing random symbols that obviously make to senseNo surprise since DEC character set does not have a greek character in its repertoire. If I'm not all mistaken DEC MCS (or similar) is the charcter set to which WE8DEC corresponds. You could check against mapping table in Locale builder, but available characters should be per following link or close enough.
    http://czyborra.com/charsets/iso8859.html#ISO-8859-1 (second chart is DEC-MCS)
    Please provide a sample of those "random symbols".
    furthermore when i connect to the db via sql developer or navicat i still get the same symbolsIf that's Oracle SQL Developer it should give a true picture of what's actually stored - which, unfortuantely, seem to be invalid character data.
    i understand it is something to do with my client system's settings but i cant work it out See above. But even if you correctly setup client environment, the db won't be able to store the data if databas character set is in fact WE8DEC.
    >
    i would really appreciate your help i am sorry if it is something very simple but i just cant find it I'm not sure, but it would seem as you have been given unfeasible conditions to work from. So maybe it's not up to you, until a character set migration has been taken place.
    In general, the Database character set should be a suitable superset (repertoire) that covers all current (and hopefully future) language alphabets requirements.
    You might want to search forum for 'we8dec' to find previous related discussions.
    Edit:
    - Added url with DEC MCS.
    - platform info
    Edited by: orafad on Jan 26, 2012 12:28 PM
    Edited by: orafad on Jan 26, 2012 12:43 PM

  • How to find Client Character set?

    Hi,
    I need to connect to remote database which is having different character set than the client. Ia there any method to display client character and Database character set from SQL Plus? Could someone please help me.
    Thanks in Advance
    Sree.

    I guess you're using PL/SQL Developer?
    (because I get that warning message too ;) )
    The warning also continues with:
    You can set the client character set thought the NLS_LANG environment variable or the NLS_LANG registry key.
    If I execute some scripts from client (client character set WE8MSWIN1252 and database character set UTF8) will
    it cause any problem?It depends on what kind of data you're loading/importing. (chinese characters for example)
    I never had any problems at all, since I'm not using 'exotic' characters.
    You can find related threads on http://asktom.oracle.com/pls/asktom/asktom.search?p_string=%22UTF8%22
    and more explanations in the Oracle Globalization Guide: http://download.oracle.com/docs/cd/B19306_01/server.102/b14225/toc.htm

  • As a webservice client, how to set character encoding for JAX-WS?

    I couldn't find the right API to set character encoding for a webservice client. What I did is
    1, wsimport which gives me MyService, MyPortType...
    2. Create new MyService
    3. Get MyPort from MyService
    4. Call myPort.myOperation with objects
    Where is the right place to set character encoding and how to set it? Thanks.
    Regards
    -Jiaqi Guo

    The .js file and the html need to have the same encoding. If
    your html uses iso-8859-7, then the .js must also use that. But if
    the original text editor created the .js file using utf-8, then
    that is what the html needs to use.

  • Client-DB character set conflict

    Hi all,
    I have a 9idb running on wink2. The NLS_CHARACTERSET are:
    DB ='AL32UTF8'
    client NLS_LANG ="American_America.WE8ISO8859P1".
    I had no trouble in reading/loading some characters (western eur.) But the data are corrupt and unreadable when it comes to manipulate eastern eur. characters (czech,slovenia..)
    I did modify the client character set from "American_America.WE8ISO8859P1" to "American_America.AL32UTF8". But i still can not properly read eastern characters.
    Please advise,
    Thks

    Hi there,
    Using sql/loader, i get data in properly by forcing the loading process to use a specific character set.
    I've added "CHARACTER SET UTF8" parameter in the control file.And saved the input file as UTF8.Data get loaded correctly.
    Question: I'm working on a test db with a unicode character set (AL32UTF8).No problem with eastern european characters.
    Our production db has a nls charac = 'WE8ISO8859P1',which supports latin-based writting script but not eastern european characters.I'm getting trouble.
    Shall I migrate the prod db character set from 'WE8ISO8859P1' to 'AL32UTF8', which is a superset in this case ?
    Could you please through some light on how i should be doing this ?
    Thkx,
    Lamine

  • Database client character set problem

    Hello
    My database oracle 11gR1 database at Linux platform
    Database NLS_LANG settings
    SQL> Select * from nls_session_parameters;
    PARAMETER VALUE
    NLS_LANGUAGE AMERICAN
    NLS_TERRITORY AMERICA
    NLS_CURRENCY $
    NLS_ISO_CURRENCY AMERICA
    NLS_NUMERIC_CHARACTERS .,
    NLS_CALENDAR GREGORIAN
    NLS_DATE_FORMAT DD-MON-RR
    NLS_DATE_LANGUAGE AMERICAN
    NLS_SORT BINARY
    NLS_TIME_FORMAT HH.MI.SSXFF AM
    NLS_TIMESTAMP_FORMAT DD-MON-RR HH.MI.SSXFF AM
    NLS_TIME_TZ_FORMAT HH.MI.SSXFF AM TZR
    NLS_TIMESTAMP_TZ_FORMAT DD-MON-RR HH.MI.SSXFF AM TZR
    NLS_DUAL_CURRENCY $
    NLS_COMP BINARY
    NLS_LENGTH_SEMANTICS BYTE
    NLS_NCHAR_CONV_EXCP FALSE
    SQL> SELECT * from NLS_DATABASE_PARAMETERS WHERE parameter IN ( 'NLS_LANGUAGE', 'NLS_TERRITORY', 'NLS_CHARACTERSET');
    PARAMETER VALUE
    NLS_LANGUAGE AMERICAN
    NLS_TERRITORY AMERICA
    NLS_CHARACTERSET WE8ISO8859P9
    SQL> Select * from v$nls_parameters ;
    NLS_LANGUAGE
    AMERICAN
    NLS_TERRITORY
    AMERICA
    NLS_CURRENCY
    $
    NLS_ISO_CURRENCY
    AMERICA
    NLS_NUMERIC_CHARACTERS
    NLS_CALENDAR
    GREGORIAN
    NLS_DATE_FORMAT
    DD-MON-RR
    NLS_DATE_LANGUAGE
    AMERICAN
    NLS_CHARACTERSET
    WE8ISO8859P9
    NLS_SORT
    BINARY
    NLS_TIME_FORMAT
    HH.MI.SSXFF AM
    NLS_TIMESTAMP_FORMAT
    DD-MON-RR HH.MI.SSXFF AM
    NLS_TIME_TZ_FORMAT
    HH.MI.SSXFF AM TZR
    NLS_TIMESTAMP_TZ_FORMAT
    DD-MON-RR HH.MI.SSXFF AM TZR
    NLS_DUAL_CURRENCY
    $
    NLS_NCHAR_CHARACTERSET
    UTF8
    NLS_COMP
    BINARY
    NLS_LENGTH_SEMANTICS
    BYTE
    NLS_NCHAR_CONV_EXCP
    FALSE
    And Client informations: Windows 7 oracle forms 10gr2 forms installation NLS_LANG=AMERICAN_AMERICA.WE8ISO8859P9
    When i insert Turkish special characters from client,everything seems okey from client side
    http://img.photobucket.com/albums/v346/satanix/moz-screenshot-1.png
    But when i select from database it seems like this.
    http://img.photobucket.com/albums/v346/satanix/moz-screenshot-2.png
    And i update this row from Linux side and select from client
    http://img.photobucket.com/albums/v346/satanix/moz-screenshot-4.png
    NLS_LANGS which i tried at windows platforms
    AMERICAN_AMERICA.WE8ISO8859P9
    AMERICAN_AMERICA.UTF8
    AMERICAN_AMERICA.TR8PC857 (Best result but still lots of problem)
    AMERICAN_AMERICA.TR8MSWIN1254
    Thanks

    Hi,
    sorry missed that picture. What I now think is that you missing the possibility to display turkish characters on Linux. Is there a Turkish pack to install for Linux "(I'm no a Linux expert). Or are you using a lettertype which cannot display Turkish letters?
    Herald ten Dam
    http://htendam.wordpress.com

  • ORA-12741: Express Instant Client: unsupported server character set LV8PC8L

    How Can I connect to database???
    I've setup a 10g XE on trustix linux 3.0.5
    Compiled oci8 and pdo_oci
    I'm trying to connect to windows database running an old Oracle 8.1 database
    Any ideas how i can read data from that database - WITHOUT MODIFYING IT ?

    I'm not clear how you're connecting but this error could mean that you don't have transalations for Latvian Version IBM-PC Code Page 866 8-bit Latin/Cyrillic (LV8PC8LR). If that's the case it masquerades as the error when the underlying error can't be rendered in the language. This is my best guess.

  • Character sets and ado

    I have a table with a clob field on an Oracle 8.1.7.4 database. When querying the clob field via odbc and ado the value is truncated. The Oracle server and client are using a WE8ISO8859P1 character set. Has anyone come across this before.
    Thanks.

    I believe the data should be able to be represented by IS0-8859. The data is a long random string of characters that represents a fingerprint image.
    We seem to only get 996 characters back from the database. If I do a getchunk on the data then I get 996 characters of data, then 996 NULLS, then 996 characters of data and so on. The 996 NULLS should be data.
    The data is in the database because I can do a dbms_lob.substr and get the correct info back.

  • Arabic Character set conversion-help needed

    We have our main database running in 10g (Solaris o/s) & planning to move these to RAC 11g.
    One of our old oracle DB(8.0.5)/solaris, which is not used till recently need to upgrade to 10g Rel2.
    I know Supported direct upgrade 8.0.6/8.1.7/9i -> 10g
    Current DB: 8.0.5 (Character Set: AR8ISO8859P6)
    Target DB : 10g Rel 2 (Character Set: AR8MSWIN1256)
    I am thinking to go the following way by using exp/imp
    8.0.5(AR8ISO8859P6) -> 8.1.7(AR8ISO8859P6) -> 10G(AR8MSWIN1256)
    OR
    8.0.5(AR8ISO8859P6) -> 8.1.7(AR8MSWIN1256) -> 10G(AR8MSWIN1256)
    please advice
    thanks

    (1) At source db 8.0.5 (solaris)
    PARAMETER VALUE
    NLS_LANGUAGE AMERICAN
    NLS_TERRITORY AMERICA
    NLS_CALENDAR GREGORIAN
    NLS_DATE_FORMAT DD-MON-YY
    NLS_DATE_LANGUAGE AMERICAN
    NLS_CHARACTERSET AR8ISO8859P6
    NLS_SORT BINARY
    NLS_NCHAR_CHARACTERSE T AR8ISO8859P6
    $set NLS_LANG=AMERICAN_AMERICA.AR8ISO8859P6
    $exp sys/dba file=full251109.dmp full=y
    (2):>> At target db 10g R2 (solaris)
    PARAMETER VALUE
    NLS_LANGUAGE AMERICAN
    NLS_TERRITORY AMERICA
    NLS_CALENDAR GREGORIAN
    NLS_DATE_FORMAT DD-MON-RRRR
    NLS_DATE_LANGUAGE AMERICAN
    NLS_CHARACTERSET AR8ISO8859P6
    NLS_SORT BINARY
    NLS_NCHAR_CHARACTERSET UTF8
    NLS_COMP BINARY
    NLS_LENGTH_SEMANTICS BYTE
    NLS_NCHAR_CONV_EXCP FALSE
    $export NLS_LANG=AMERICAN_AMERICA.AR8ISO8859P6
    $imp testdba/testdba file=full251105.dmp fromuser=PROFINAL touser=PROFINAL
    *$csscan testdba/testdba FULL=Y FROMCHAR=AR8ISO8859P6 TOCHAR=AR8ISO8859P6 LOG=P6check CAPTURE=Y ARRAY=100000 PROCESS=2*
    There is EXCEPTIONAL DATA in .err file+
    clients accessing 8.0.5 dataabase uses characterset AR8IS08859P6, which is SAME as 8.0.5 database
    -CSSCAN result->>[Database Scan Parameters]
    Parameter Value
    CSSCAN Version v2.1
    Instance Name MIG1
    Database Version 10.2.0.1.0
    Scan type Full database
    Scan CHAR data? YES
    Database character set AR8ISO8859P6
    FROMCHAR AR8ISO8859P6
    TOCHAR AR8ISO8859P6
    Scan NCHAR data? NO
    Array fetch buffer size 100000
    Number of processes 2
    Capture convertible data? YES
    [Scan Summary]
    Some character type data in the data dictionary are not convertible to the new
    haracter set Some character type application data are not convertible to the new characters
    [Data Dictionary Conversion Summary]
    Datatype Changeless Convertible Truncation Lossy
    VARCHAR2 2,235,403 0 0 *1,492*
    CHAR 1,097 0 0 0
    LONG 155,188 0 0 6
    CLOB 24,643 0 0 0
    VARRAY 21,352 0 0 0
    Total 2,437,683 0 0 1,498
    Total in percentage 99.939% 0.000% 0.000% 0.061%
    The data dictionary can not be safely migrated using the CSALTER script
    [Application Data Conversion Summary]
    Datatype Changeless Convertible Truncation Lossy
    VARCHAR2 16,986,594 0 0 *1,240,383*
    CHAR 164,114 0 0 0
    LONG 7 0 0 0
    CLOB 1 0 0 0
    VARRAY 1,436 0 0 0
    Total in percentage 93.256% 0.000% 0.000%
    6.744%
    [Distribution of Convertible, Truncated and Lossy Data by Table]
    USER.TABLE Convertible Truncation Lossy
    PROFINAL.BASE_MASTER_DATAS 0 0 *362,003*
    PROFINAL.CODE_ALLOW 0 0 *53*
    PROFINAL.CODE_ALLOWANCE_TYPES 0 0 *1*
    PROFINAL.CODE_BONUS_TYPES 0 0 *2*
    PROFINAL.CODE_BRANCHES 0 0 *2*
    PROFINAL.CODE_CERTIFICATES 0 0 *94*
    Kindly help,,,
    Edited by: userR12 on Nov 25, 2009 1:43 AM
    Edited by: userR12 on Nov 25, 2009 1:52 AM

  • Character Set Error in PL/SQL

    Hi,
    While connecting to PL/SQL Developer I am getting this following error.
    Database character set (AL32UTF8) and client character set (WE8MSWIN1252) are different.
    Character set conversion may cause unexpected results.
    Note: you can set the client character set through the NLS_LANG registry key in
    HKEY_LOCAL_MACHINE\SOFTWARE\ORACLE\KEY_XE.
    Please help me avoid this error.
    Thanks.

    That is presumably a PL/SQL Developer error. You may want to contact the vendor of that particular product to understand that warning because it makes no sense to me.
    It is perfectly appropriate, and quite normal, for the client character set to be a subset of the database character set. Setting the client character set to match the database character set can create a host of problems that lead to invalid data being stored in the database. This appears designed to increase the odds that this particular tool will work correctly while decreasing the odds that everything else in your environment will work correctly. That seems like a relatively poor trade-off to me.
    Justin

  • Character set migration error to UTF8 urgent

    Hi
    when we migrated from ar8iso889p6 to utf8 characterset we are facing one error when i try to compile one package through forms i am getting error program unit pu not found.
    When i running the source code of that procedure direct from database using sqlplus its running wihtout any problem.How can i migrate this forms from ar8iso889p6 to utf8 characterset. We migrated from databas with ar8iso889p6 oracle 81.7 database to oracle 9.2. database with character set UTF8 (windows 2000) export and import done without any error
    I am using oracle 11i inside the calling forms6i and reports 6i
    with regards
    ramya
    1) this is server side program yaa when connecting with forms i am getting error .When i am running this program using direct sql its working when i running compiling i am getting this error.
    3) yes i am using 11 i (11.5.10) inside its calling forms 6i and reports .Why this is giving problem using forms.Is there any setting changing in forms nls_lang
    with regards

    Hi Ramya
    what i understand from your question is that you are trying to compile a procedure from a forms interface at client side?
    if yes you should check the code in the forms that is calling the compilation package.
    does it contains strings that might be affected from the character set change???
    Tony G.

  • NLS CHARACTER SET 변경 방법 (ORACLE 7)

    제품 : ORACLE SERVER
    작성날짜 : 2004-11-09
    NLS CHARACTER SET 변경 방법 (ORACLE 7)
    ======================================
    PURPOSE
    이 자료는 Oracle RDBMS SERVER에서 NLS CHARACTER SET 변경 방법에 대한
    내용을 소개한다.
    [ ORACLE 7 에서만 가능 ]
    데이타베이스의 CHARACTER SET은 데이타 딕셔너리 테이블인 sys.props$에
    들어 있다.
    SQL>desc sys.props$
    Name Null? Type
    NAME NOT NULL VARCHAR2(30)
    VALUE$ VARCHAR2(2000)
    COMMENT$ VARCHAR2(2000)
    SQL>column c1 format a30
    SQL>select name c1, value$ c1 from sys.props$;
    C1 C1
    DICT.BASE 2
    NLS_LANGUAGE AMERICAN
    NLS_TERRITORY AMERICA
    NLS_CURRENCY $
    NLS_ISO_CURRENCY AMERICA
    NLS_NUMERIC_CHARACTERS .,
    NLS_DATE_FORMAT DD-MON-YY
    NLS_DATE_LANGUAGE AMERICAN
    NLS_CHARACTERSET US7ASCII
    NLS_SORT BINARY
    GLOBAL_DB_NAME NLSV7.WORLD
    여기서 NLS_CHARACTERSET에 현재 DB의 CHARACTER SET이 들어 있는데
    이 값을 변경하여 DB의 CHARACTER SET을 변경할 수 있다.
    여기서는 US7ASCII에서 KO16KSC5601로 옮기는 경우를 알아보자.
    우선 바꾸고자 하는 CHRACTER SET이 지원되는 지를 다음 명령으로
    확인한다.
    select convert('a','KO16KSC5601','US7ASCII') from dual;
    만약 이 Select 문에서 ORA-01482 에러가 발생하면 지정한 CHARACTER
    SET이 지원되지 않는 경우이며 에러가 발생하지 않으면 CHARACTER
    SET을 변경할 수 있다.
    작업을 하기 전에는 만약을 위해서 DB 전체를 백업 받아두도록 한다.
    CHARACTER SET 을 잘못 변경하면 DB 를 OPEN 할 수가 없기 때문이다.
    1. 다음의 Update문을 실행하여 CHARACTER SET을 변경한다.
    UPDATE sys.props$
    SET value$ = 'KO16KSC5601'
    WHERE name = 'NLS_CHARACTERSET';
    Update 시에 NLS_CHARACTERSET을 지원되지 않는 값으로 잘못 설정하거나
    실수로 콘트롤 문자 같은 것이 들어가게 되면 DB가 Shutdown 된 다음에는
    Startup 이 안되므로 Update 후에 다음 명령으로 확인을 한 다음에
    Commit을 하도록 한다.
    select name, value$
    from sys.props$
    where value$ = 'KO16KSC5601';
    Select가 제대로 출력되면 Commit 하고 Shutdown 했다가 Startup 하게
    되면 새로운 CHARACTER SET 값을 갖게 된다. SELECT가 안 되면 ROLLBACK
    하고 UPDATE부터 다시 하도록 한다.
    2. 환경 변수 NLS_LANG 을 변경한다.
    .profile 에서
    NLS_LANG=American_America.KO16KSC5601; export NLS_LANG
    또는 .cshrc 에서.
    setenv NLS_LANG American_America.KO16KSC5601
    *** win95 및 winnt의 client에서는 registry editor에서 NLS_LANG 값을
    맞추어준다.
    주의 !!!
    : 위의 작업을 하기 전에 발생할 가능성이 있는 문제점
    1) update 중 KO16KSC5601 이나 US7ASCII 등에서 철자를 잘못 입력하시면,
    db 재기동 후에, 다음과 같은 에러가 발생합니다.
    ora-12708
    12708, 00000, "error while loading create database NLS parameter %s"
    2) KO16KSC5601과 US7ASCII의 비교
    Character set : KO16KSC5601 인 경우
    ===================================
    : double byte encoding schema 이므로, 한글의 경우 2 bytes 를 크기 1로
    계산하는 함수들이 있습니다.
    그리고, table , column name에 한글을 double quote 없이 사용할 수 있습니다.
    예)
    SQL> create table 시험1
    2 (컬럼1 varchar(10));

    a
    홍길동
    SQL> select length(컬럼1) from 시험1;
    1
    1
    3
    SQL> select lengthb(컬럼1) from 시험1;
    2
    1
    6
    Character set : US7ASCII 인 경우
    =================================
    : single byte 7 bit encoding 을 사용합니다.
    한글로 된 table, column 이름 사용 시 double quote를 반드시 사용해야 한다.
    예)
    SQL> create table "사원"
    2 ("사원이름" varchar2(10));

    a
    홍길동
    SQL> select length("사원이름") from "사원";
    2
    1
    6
    SQL> select lengthb("사원이름") from "사원";
    2
    1
    6
    US7ASCII일 때에는 vsize, lengthb function의 결과가 length 함수와 모두
    동일합니다.
    cf) substr, substrb 함수도 위의 length, lengthb의 관계와 같음.

    제품 : ORACLE SERVER
    작성날짜 : 2004-11-09
    NLS CHARACTER SET 변경 방법 (ORACLE 7)
    ======================================
    PURPOSE
    이 자료는 Oracle RDBMS SERVER에서 NLS CHARACTER SET 변경 방법에 대한
    내용을 소개한다.
    [ ORACLE 7 에서만 가능 ]
    데이타베이스의 CHARACTER SET은 데이타 딕셔너리 테이블인 sys.props$에
    들어 있다.
    SQL>desc sys.props$
    Name Null? Type
    NAME NOT NULL VARCHAR2(30)
    VALUE$ VARCHAR2(2000)
    COMMENT$ VARCHAR2(2000)
    SQL>column c1 format a30
    SQL>select name c1, value$ c1 from sys.props$;
    C1 C1
    DICT.BASE 2
    NLS_LANGUAGE AMERICAN
    NLS_TERRITORY AMERICA
    NLS_CURRENCY $
    NLS_ISO_CURRENCY AMERICA
    NLS_NUMERIC_CHARACTERS .,
    NLS_DATE_FORMAT DD-MON-YY
    NLS_DATE_LANGUAGE AMERICAN
    NLS_CHARACTERSET US7ASCII
    NLS_SORT BINARY
    GLOBAL_DB_NAME NLSV7.WORLD
    여기서 NLS_CHARACTERSET에 현재 DB의 CHARACTER SET이 들어 있는데
    이 값을 변경하여 DB의 CHARACTER SET을 변경할 수 있다.
    여기서는 US7ASCII에서 KO16KSC5601로 옮기는 경우를 알아보자.
    우선 바꾸고자 하는 CHRACTER SET이 지원되는 지를 다음 명령으로
    확인한다.
    select convert('a','KO16KSC5601','US7ASCII') from dual;
    만약 이 Select 문에서 ORA-01482 에러가 발생하면 지정한 CHARACTER
    SET이 지원되지 않는 경우이며 에러가 발생하지 않으면 CHARACTER
    SET을 변경할 수 있다.
    작업을 하기 전에는 만약을 위해서 DB 전체를 백업 받아두도록 한다.
    CHARACTER SET 을 잘못 변경하면 DB 를 OPEN 할 수가 없기 때문이다.
    1. 다음의 Update문을 실행하여 CHARACTER SET을 변경한다.
    UPDATE sys.props$
    SET value$ = 'KO16KSC5601'
    WHERE name = 'NLS_CHARACTERSET';
    Update 시에 NLS_CHARACTERSET을 지원되지 않는 값으로 잘못 설정하거나
    실수로 콘트롤 문자 같은 것이 들어가게 되면 DB가 Shutdown 된 다음에는
    Startup 이 안되므로 Update 후에 다음 명령으로 확인을 한 다음에
    Commit을 하도록 한다.
    select name, value$
    from sys.props$
    where value$ = 'KO16KSC5601';
    Select가 제대로 출력되면 Commit 하고 Shutdown 했다가 Startup 하게
    되면 새로운 CHARACTER SET 값을 갖게 된다. SELECT가 안 되면 ROLLBACK
    하고 UPDATE부터 다시 하도록 한다.
    2. 환경 변수 NLS_LANG 을 변경한다.
    .profile 에서
    NLS_LANG=American_America.KO16KSC5601; export NLS_LANG
    또는 .cshrc 에서.
    setenv NLS_LANG American_America.KO16KSC5601
    *** win95 및 winnt의 client에서는 registry editor에서 NLS_LANG 값을
    맞추어준다.
    주의 !!!
    : 위의 작업을 하기 전에 발생할 가능성이 있는 문제점
    1) update 중 KO16KSC5601 이나 US7ASCII 등에서 철자를 잘못 입력하시면,
    db 재기동 후에, 다음과 같은 에러가 발생합니다.
    ora-12708
    12708, 00000, "error while loading create database NLS parameter %s"
    2) KO16KSC5601과 US7ASCII의 비교
    Character set : KO16KSC5601 인 경우
    ===================================
    : double byte encoding schema 이므로, 한글의 경우 2 bytes 를 크기 1로
    계산하는 함수들이 있습니다.
    그리고, table , column name에 한글을 double quote 없이 사용할 수 있습니다.
    예)
    SQL> create table 시험1
    2 (컬럼1 varchar(10));

    a
    홍길동
    SQL> select length(컬럼1) from 시험1;
    1
    1
    3
    SQL> select lengthb(컬럼1) from 시험1;
    2
    1
    6
    Character set : US7ASCII 인 경우
    =================================
    : single byte 7 bit encoding 을 사용합니다.
    한글로 된 table, column 이름 사용 시 double quote를 반드시 사용해야 한다.
    예)
    SQL> create table "사원"
    2 ("사원이름" varchar2(10));

    a
    홍길동
    SQL> select length("사원이름") from "사원";
    2
    1
    6
    SQL> select lengthb("사원이름") from "사원";
    2
    1
    6
    US7ASCII일 때에는 vsize, lengthb function의 결과가 length 함수와 모두
    동일합니다.
    cf) substr, substrb 함수도 위의 length, lengthb의 관계와 같음.

  • ORA-12709: error while loading create database character set

    I installed Oracle 8.05 on Linux successfully: was able to login
    whith SQLPlus, start and stop the db whith svrmgrl etc.
    During this install I chose WE8ISO8859P9 as the database
    characterset when prompted.
    After that I installed Oracle Application Server 3.02, and now
    I'm getting the
    ORA-12709: error while loading create database character set
    message when I try to start up the database, and the database
    won't mount.
    Platform is RedHat Linux 5.2.
    NLS_LANG set to different settings,
    e.g. AMERICAN_AMERICA.WE8ISO8859P9
    but without success.
    Anyone any clue?
    Thanks!
    null

    Jogchum Reitsma (guest) wrote:
    : I installed Oracle 8.05 on Linux successfully: was able to
    login
    : whith SQLPlus, start and stop the db whith svrmgrl etc.
    : During this install I chose WE8ISO8859P9 as the database
    : characterset when prompted.
    : After that I installed Oracle Application Server 3.02, and now
    : I'm getting the
    : ORA-12709: error while loading create database character set
    : message when I try to start up the database, and the database
    : won't mount.
    : Platform is RedHat Linux 5.2.
    : NLS_LANG set to different settings,
    : e.g. AMERICAN_AMERICA.WE8ISO8859P9
    : but without success.
    : Anyone any clue?
    : Thanks!
    You can create the database with WE8DEC character set
    and to use the WE8ISO8859P9 on the client or even on Linux.
    The NLS_LANG setting doesn't effect the database, but the
    interface with the database. The same setting can be used in de
    windows 95/98/NT registry.
    null

  • Fixing a US7ASCII - WE8ISO8859P1 Character Set Conversion Disaster

    In hopes that it might be helpful in the future, here's the procedure I followed to fix  a disastrous unintentional US7ASCII on 9i to WE8ISO8859P1 on 10g migration.
    BACKGROUND
    Oracle has multiple character sets, ranging from US7ASCII to AL32UTF16.
    US7ASCII, of course, is a cheerful 7 bit character set, holding the basic ASCII characters sufficient for the English language.
    However, it also has a handy feature: character fields under US7ASCII will accept characters with values > 128. If you have a web application, users can type (or paste) Us with umlauts, As with macrons, and quite a few other funny-looking characters.
    These will be inserted into the database, and then -- if appropriately supported -- can be selected and displayed by your app.
    The problem is that while these characters can be present in a VARCHAR2 or CLOB column, they are not actually legal. If you try within Oracle to convert from US7ASCII to WE8ISO8859P1 or any other character set, Oracle recognizes that these characters with values greater than 127 are not valid, and will replace them with a default "unknown" character. In the case of a change from US7ASCII to WE8ISO8859P1, it will change them to 191, the upside down question mark.
    Oracle has a native utility, introduced in 8i, called csscan, which assists in migrating to different character sets. This has been replaced in newer versions with the Database MIgration Assistant for Unicode (DMU), which is the new recommended tool for 11.2.0.3+.
    These tools, however, do no good unless they are run. For my particular client, the operations team took a database running 9i and upgraded it to 10g, and as part of that process the character set was changed from US7ASCII to WE8ISO8859P1. The database had a large number of special characters inserted into it, and all of these abruptly turned into upside-down question marks. The users of the application didn't realize there was a problem until several weeks later, by which time they had put a lot of new data into the system. Rollback was not possible.
    FIXING THE PROBLEM
    How fixable this problem is and the acceptable methods which can be used depend on the application running on top of the database. Fortunately, the client app was amenable.
    (As an aside note: this approach does not use csscan -- I had done something similar previously on a very old system and decided it would take less time in this situation to revamp my old procedures and not bring a new utility into the mix.)
    We will need to separate approaches -- one to fix the VARCHAR2 & CHAR fields,  and a second for CLOBs.
    In order to set things up, we created two environments. The first was a clone of production as it is now, and the second a clone from before the upgrade & character set change. We will call these environments PRODCLONE and RESTORECLONE.
    Next, we created a database link, OLD6. This allows PRODCLONE to directly access RESTORECLONE. Since they were cloned with the same SID, establishing the link needed the global_names parameter set to false.
    alter system set global_names=false scope=memory;
    CREATE PUBLIC DATABASE LINK OLD6
    CONNECT TO DBUSERNAME
    IDENTIFIED BY dbuserpass
    USING 'restoreclone:1521/MYSID';
    Testing the link...
    SQL> select count(1) from users@old6;
      COUNT(1)
           454
    Here is a row in a table which contains illegal characters. We are accessing RESTORECLONE from PRODCLONE via our link.
    PRODCLONE> select dump(title) from my_contents@old6 where pk1=117286;
    DUMP(TITLE)
    Typ=1 Len=49: 78,67,76,69,88,45,80,78,174,32,69,120,97,109,32,83,116,121,108,101
    ,32,73,110,116,101,114,97,99,116,105,118,101,32,82,101,118,105,101,119,32,81,117
    ,101,115,116,105,111,110,115
    By comparison, a dump of that row on PRODCLONE's my_contents gives:
    PRODCLONE> select dump(title) from my_contents where pk1=117286;
    DUMP(TITLE)
    Typ=1 Len=49: 78,67,76,69,88,45,80,78,191,32,69,120,97,109,32,83,116,121,108,101
    ,32,73,110,116,101,114,97,99,116,105,118,101,32,82,101,118,105,101,119,32,81,117
    ,101,115,116,105,111,110,115
    Note that the "174" on RESTORECLONE was changed to "191" on PRODCLONE.
    We can manually insert CHR(174) into our PRODCLONE and have it display successfully in the application.
    However, I tried a number of methods to copy the data from RESTORECLONE to PRODCLONE through the link, but entirely without success. Oracle would recognize the character as invalid and silently transform it.
    Eventually, I located a clever workaround at this link:
    https://kr.forums.oracle.com/forums/thread.jspa?threadID=231927
    It works like this:
    On RESTORECLONE you create a view, vv, with UTL_RAW:
    RESTORECLONE> create or replace view vv as select pk1,utl_raw.cast_to_raw(title) as title from my_contents;
    View created.
    This turns the title to raw on the RESTORECLONE.
    You can now convert from RAW to VARCHAR2 on the PRODCLONE database:
    PRODCLONE> select dump(utl_raw.cast_to_varchar2 (title)) from vv@old6 where pk1=117286;
    DUMP(UTL_RAW.CAST_TO_VARCHAR2(TITLE))
    Typ=1 Len=49: 78,67,76,69,88,45,80,78,174,32,69,120,97,109,32,83,116,121,108,101
    ,32,73,110,116,101,114,97,99,116,105,118,101,32,82,101,118,105,101,119,32,81,117
    ,101,115,116,105,111,110,115
    The above works because oracle on PRODCLONE never knew that our TITLE string on RESTORE was originally in  US7ASCII, so it was unable to do its transparent character set conversion.
    PRODCLONE> update my_contents set title=( select utl_raw.cast_to_varchar2 (title) from vv@old6 where pk1=117286) where pk1=117286;
    PRODCLONE> select dump(title) from my_contents where pk1=117286;
    DUMP(UTL_RAW.CAST_TO_VARCHAR2(TITLE))
    Typ=1 Len=49: 78,67,76,69,88,45,80,78,174,32,69,120,97,109,32,83,116,121,108,101
    ,32,73,110,116,101,114,97,99,116,105,118,101,32,82,101,118,105,101,119,32,81,117
    ,101,115,116,105,111,110,115
    Excellent! The "174" character has survived the transfer and is now in place on PRODCLONE.
    Now that we have a method to move the data over, we have to identify which columns /tables have character data that was damaged by the conversion. We decided we could ignore anything with a length smaller than 10 -- such fields in our application would be unlikely to have data with invalid characters.
    RESTORECLONE> select count(1) from user_tab_columns where data_type in ('CHAR','VARCHAR2') and data_length > 10;
       COUNT(1)
        533
    By converting a field to WE8ISO8859P1, and then comparing it with the original, we can see if the characters change:
    RESTORECLONE> select count(1) from my_contents where title != convert (title,'WE8ISO8859P1','US7ASCII') ;
      COUNT(1)
         10568
    So 10568 rows have characters which were transformed  into 191s as part of the original conversion.
    [ As an aside, we can't use CONVERT() on LOBs -- for them we will need another approach, outlined further below.
    RESTOREDB> select count(1) from my_contents where main_data != convert (convert(main_DATA,'WE8ISO8859P1','US7ASCII'),'US7ASCII','WE8ISO8859P1') ;
    select count(1) from my_contents where main_data != convert (convert(main_DATA,'WE8ISO8859P1','US7ASCII'),'US7ASCII','WE8ISO8859P1')
    ERROR at line 1:
    ORA-00932: inconsistent datatypes: expected - got CLOB
    Anyway, now that we can identify VARCHAR2 fields which need to be checked, we can put together a PL/SQL stored procedure to do it for us:
    create or replace procedure find_us7_strings
    (table_name varchar2,
    fix_col varchar2 )
    authid current_user
    as
    orig_sql varchar2(1000);
    begin
    orig_sql:='insert into cnv_us7(mytablename,myindx,mycolumnname)  select '''||table_name||''',pk1,'''||fix_col||''' from '||table_name||' where '||fix_col||' !=  CONVERT(CONVERT('||fix_col||',''WE8ISO8859P1''),''US7ASCII'') and '||fix_col||' is not null';
    -- Uncomment if debugging:
    -- dbms_output.put_line(orig_sql);
      execute immediate orig_sql;
    end;
    And create a table to store the information as to which tables, columns, and rows have the bad characters:
    drop table cnv_us7;
    create table cnv_us7 (mytablename varchar2(50), myindx number,      mycolumnname varchar2(50) ) tablespace myuser_data;
    create index list_tablename_idx on cnv_us7(mytablename) tablespace myuser_indx;
    With a SQL-generating SQL script, we can iterate through all the tables/columns we want to check:
    --example of using the data: select title from my_contents where pk1 in (select myindx from cnv_us7)
    set head off pagesize 1000 linesize 120
    spool runme.sql
    select 'exec find_us7_strings ('''||table_name||''','''||column_name||'''); ' from user_tab_columns
          where
              data_type in ('CHAR','VARCHAR2')
              and table_name in (select table_name from user_tab_columns where column_name='PK1' and  table_name not  in ('HUGETABLEIWANTTOEXCLUDE','ANOTHERTABLE'))
              and char_length > 10
              order by table_name,column_name;
    spool off;
    set echo on time on timing on feedb on serveroutput on;
    spool output_of_runme
    @./runme.sql
    spool off;
    Which eventually gives us the following inserted into CNV_US7:
    20:48:21 SQL> select count(1),mycolumnname,mytablename from cnv_us7 group by mytablename,mycolumnname;
             4 DESCRIPTION                                        MY_FORUMS
         21136 TITLE                                              MY_CONTENTS
    Out of 533 VARCHAR2s and CHARs, we only had five or six columns that needed fixing
    We create our views on  RESTOREDB:
    create or replace view my_forums_vv as select pk1,utl_raw.cast_to_raw(description) as description from forum_main;
    create or replace view my_contents_vv as select pk1,utl_raw.cast_to_raw(title) as title from my_contents;
    And then we can fix it directly via sql:
    update my_contents taborig1 set TITLE= (select utl_raw.cast_to_varchar2 (TITLE) from my_contents_vv@old6 where pk1=taborig1.pk1)
    where pk1 in (
    select tabnew.pk1 from my_contents@old6 taborig,my_contents tabnew,cnv_us7@old6
          where taborig.pk1=tabnew.pk1
              and myindx=tabnew.pk1
              and mycolumnname='TITLE'
              and mytablename='MY_CONTENTS'
              and convert(taborig.TITLE,'US7ASCII','WE8ISO8859P1') = tabnew.TITLE );
    Note this part:
          "and convert(taborig.TITLE,'US7ASCII','WE8ISO8859P1') = tabnew.TITLE "
    This checks to verify that the TITLE field on the PRODCLONE and RESTORECLONE are the same (barring character set issues). This is there  because if the users have changed TITLE  -- or any other field -- on their own between the time of the upgrade and now, we do not want to overwrite their changes. We make the assumption that as part of the process, they may have changed the bad character on their own.
    We can also create a stored procedure which will execute the SQL for us:
    create or replace procedure fix_us7_strings
    (TABLE_NAME varchar2,
    FIX_COL varchar2 )
    authid current_user
    as
    orig_sql varchar2(1000);
    TYPE cv_type IS REF CURSOR;
    orig_cur cv_type;
    begin
    orig_sql:='update '||TABLE_NAME||' taborig1 set '||FIX_COL||'= (select utl_raw.cast_to_varchar2 ('||FIX_COL||') from '||TABLE_NAME||'_vv@old6 where pk1=taborig1.pk1)
    where pk1 in (
    select tabnew.pk1 from '||TABLE_NAME||'@old6 taborig,'||TABLE_NAME||' tabnew,cnv_us7@old6
          where taborig.pk1=tabnew.pk1
              and myindx=tabnew.pk1
              and mycolumnname='''||FIX_COL||'''
              and mytablename='''||TABLE_NAME||'''
              and convert(taborig.'||FIX_COL||',''US7ASCII'',''WE8ISO8859P1'') = tabnew.'||FIX_COL||')';
    dbms_output.put_line(orig_sql);
    execute immediate orig_sql;
    end;
    exec fix_us7_strings('MY_FORUMS','DESCRIPTION');
    exec fix_us7_strings('MY_CONTENTS','TITLE');
    commit;
    To validate this before and after, we can run something like:
    select dump(description) from my_forums where pk1 in (select myindx from cnv_us7@old6 where mytablename='MY_FORUMS');
    The above process fixes all the VARCHAR2s and CHARs. Now what about the CLOB columns?
    Note that we're going to have some extra difficulty here, not just because we are dealing with CLOBs, but because we are working with CLOBs in 9i, whose functions have less CLOB-related functionality.
    This procedure finds invalid US7ASCII strings inside a CLOB in 9i:
    create or replace procedure find_us7_clob
    (table_name varchar2,
    fix_col varchar2)
    authid current_user
    as
      orig_sql varchar2(1000);
      type cv_type is REF CURSOR;
      orig_table_cur cv_type;
      my_chars_read NUMBER;
      my_offset NUMBER;
      my_problem NUMBER;
      my_lob_size NUMBER;
      my_indx_var NUMBER;
      my_total_chars_read NUMBER;
      my_output_chunk VARCHAR2(4000);
      my_problem_flag NUMBER;
      my_clob CLOB;
      my_total_problems NUMBER;
      ins_sql VARCHAR2(4000);
    BEGIN
       DBMS_OUTPUT.ENABLE(1000000);
       orig_sql:='select pk1,dbms_lob.getlength('||FIX_COL||') as cloblength,'||fix_col||' from '||table_name||' where dbms_lob.getlength('||fix_col||') >0 and '||fix_col||' is not null order by pk1';
       open orig_table_cur for orig_sql;
       my_total_problems := 0;
       LOOP
            FETCH orig_table_cur INTO my_indx_var,my_lob_size,my_clob;
                    EXIT WHEN orig_table_cur%NOTFOUND;
            my_offset :=1;
            my_chars_read := 512;
            my_problem_flag :=0;
            WHILE my_offset < my_lob_size and my_problem_flag =0
                    LOOP
                    DBMS_LOB.READ(my_clob,my_chars_read,my_offset,my_output_chunk);
                    my_offset := my_offset + my_chars_read;
                    IF my_output_chunk != CONVERT(CONVERT(my_output_chunk,'WE8ISO8859P1'),'US7ASCII')
                            THEN
                            -- DBMS_OUTPUT.PUT_LINE('Problem with '||my_indx_var);
                            -- DBMS_OUTPUT.PUT_LINE(my_output_chunk);
                            my_problem_flag:=1;
                    END IF;
            END LOOP;
            IF my_problem_flag=1
                    THEN my_total_problems := my_total_problems +1;
                    ins_sql:='insert into cnv_us7(mytablename,myindx,mycolumnname) values ('''||table_name||''','||my_indx_var||','''||fix_col||''')';
                    execute immediate ins_sql;
                    END IF;
       END LOOP;
       DBMS_OUTPUT.PUT_LINE('We found '||my_total_problems||' problem rows in table '||table_name||', column '||fix_col||'.');
    END;
    And we can use SQL-generating SQL to find out which CLOBs have issues, out of all the ones in the database:
    RESTOREDB> select 'exec find_us7_clob('''||table_name||''','''||column_name||''');' from user_tab_columns where data_type='CLOB';
    exec find_us7_clob('MY_CONTENTS','DATA');
    After completion, the CNV_US7 table looked like this:
    RESTOREDB> set linesize 120 pagesize 100;
    RESTOREDB>  select count(1),mytablename,mycolumnname from cnv_us7
       where mytablename||' '||mycolumnname in (select table_name||' '||column_name from user_tab_columns
             where data_type='CLOB' )
          group by mytablename,mycolumnname;
      COUNT(1) MYTABLENAME                                        MYCOLUMNNAME
         69703 MY_CONTENTS                                  DATA
    On RESTOREDB, our 9i version, we will use this procedure (found many years ago on the internet):
    create or replace procedure CLOB2BLOB (p_clob in out nocopy clob, p_blob in out nocopy blob) is
    -- transforming CLOB to BLOB
    l_off number default 1;
    l_amt number default 4096;
    l_offWrite number default 1;
    l_amtWrite number;
    l_str varchar2(4096 char);
    begin
    loop
    dbms_lob.read ( p_clob, l_amt, l_off, l_str );
    l_amtWrite := utl_raw.length ( utl_raw.cast_to_raw( l_str) );
    dbms_lob.write( p_blob, l_amtWrite, l_offWrite,
    utl_raw.cast_to_raw( l_str ) );
    l_offWrite := l_offWrite + l_amtWrite;
    l_off := l_off + l_amt;
    l_amt := 4096;
    end loop;
    exception
    when no_data_found then
    NULL;
    end;
    We can test out the transformation of CLOBs to BLOBs with a single row like this:
    drop table my_contents_lob;
    Create table my_contents_lob (pk1 number,data blob);
    DECLARE
          v_clob CLOB;
          v_blob BLOB;
        BEGIN
          SELECT data INTO v_clob FROM my_contents WHERE pk1 = 16 ;
          INSERT INTO my_contents_lob (pk1,data) VALUES (16,empty_blob() );
          SELECT data INTO v_blob FROM my_contents_lob WHERE pk1=16 FOR UPDATE;
          clob2blob (v_clob, v_blob);
        END;
    select dbms_lob.getlength(data) from my_contents_lob;
    DBMS_LOB.GETLENGTH(DATA)
                                 329
    SQL> select utl_raw.cast_to_varchar2(data) from my_contents_lob;
    UTL_RAW.CAST_TO_VARCHAR2(DATA)
    Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam...
    Now we need to push it through a loop. Unfortunately, I had trouble making the "SELECT INTO" dynamic. Thus I used a version of the procedure for each table. It's aesthetically displeasing, but at least it worked.
    create table my_contents_lob(pk1 number,data blob);
    create index my_contents_lob_pk1 on my_contents_lob(pk1) tablespace my_user_indx;
    create or replace procedure blob_conversion_my_contents
    (table_name varchar2,
    fix_col varchar2)
    authid current_user
    as
      orig_sql varchar2(1000);
      type cv_type is REF CURSOR;
      orig_table_cur cv_type;
      my_chars_read NUMBER;
      my_offset NUMBER;
      my_problem NUMBER;
      my_lob_size NUMBER;
      my_indx_var NUMBER;
      my_total_chars_read NUMBER;
      my_output_chunk VARCHAR2(4000);
      my_problem_flag NUMBER;
      my_clob CLOB;
      my_blob BLOB;
      my_total_problems NUMBER;
      new_sql VARCHAR2(4000);
    BEGIN
      DBMS_OUTPUT.ENABLE(1000000);
       orig_sql:='select pk1,dbms_lob.getlength('||FIX_COL||') as cloblength,'||fix_col||' from '||table_name||' where pk1 in (select myindx from cnv_us7 where mytablename='''||TABLE_NAME||''' and mycolumnname='''||FIX_COL||''') order by pk1';
       open orig_table_cur for orig_sql;
       LOOP
            FETCH orig_table_cur INTO my_indx_var,my_lob_size,my_clob;
                    EXIT WHEN orig_table_cur%NOTFOUND;
            new_sql:='INSERT INTO '||table_name||'_lob(pk1,'||fix_col||') values ('||my_indx_var||',empty_blob() )';
            dbms_output.put_line(new_sql);
          execute immediate new_sql;
    -- Here's the bit that I had trouble making dynamic. Feel free to let me know what I am doing wrong.
    -- new_sql:='SELECT '||fix_col||' INTO my_blob from '||table_name||'_lob where pk1='||my_indx_var||' FOR UPDATE';
    --        dbms_output.put_line(new_sql);
            select data into my_blob from my_contents_lob where pk1=my_indx_var FOR UPDATE;
          clob2blob(my_clob,my_blob);
       END LOOP;
       CLOSE orig_table_cur;
      DBMS_OUTPUT.PUT_LINE('Completed program');
    END;
    exec blob_conversion_my_contents('MY_CONTENTS','DATA');
    Verify that things work properly:
    select dump( utl_raw.cast_to_varchar2(data))  from my_contents_lob where pk1=xxxx;
    This should let you see see characters > 150. Thus, the method works.
    We can now take this data, export it from RESTORECLONE
    exp file=a.dmp buffer=4000000 userid=system/XXXXXX tables=my_user.my_contents rows=y
    and import the data on prodclone
    imp file=a.dmp fromuser=my_user touser=my_user userid=system/XXXXXX buffer=4000000;
    For paranoia's sake, double check that it worked properly:
    select dump( utl_raw.cast_to_varchar2(data))  from my_contents_lob;
    On our 10g PRODCLONE, we'll use these stored procedures:
    CREATE OR REPLACE FUNCTION CLOB2BLOB(L_CLOB CLOB) RETURN BLOB IS
    L_BLOB BLOB;
    L_SRC_OFFSET NUMBER;
    L_DEST_OFFSET NUMBER;
    L_BLOB_CSID NUMBER := DBMS_LOB.DEFAULT_CSID;
    V_LANG_CONTEXT NUMBER := DBMS_LOB.DEFAULT_LANG_CTX;
    L_WARNING NUMBER;
    L_AMOUNT NUMBER;
    BEGIN
    DBMS_LOB.CREATETEMPORARY(L_BLOB, TRUE);
    L_SRC_OFFSET := 1;
    L_DEST_OFFSET := 1;
    L_AMOUNT := DBMS_LOB.GETLENGTH(L_CLOB);
    DBMS_LOB.CONVERTTOBLOB(L_BLOB,
    L_CLOB,
    L_AMOUNT,
    L_SRC_OFFSET,
    L_DEST_OFFSET,
    1,
    V_LANG_CONTEXT,
    L_WARNING);
    RETURN L_BLOB;
    END;
    CREATE OR REPLACE FUNCTION BLOB2CLOB(L_BLOB BLOB) RETURN CLOB IS
    L_CLOB CLOB;
    L_SRC_OFFSET NUMBER;
    L_DEST_OFFSET NUMBER;
    L_BLOB_CSID NUMBER := DBMS_LOB.DEFAULT_CSID;
    V_LANG_CONTEXT NUMBER := DBMS_LOB.DEFAULT_LANG_CTX;
    L_WARNING NUMBER;
    L_AMOUNT NUMBER;
    BEGIN
    DBMS_LOB.CREATETEMPORARY(L_CLOB, TRUE);
    L_SRC_OFFSET := 1;
    L_DEST_OFFSET := 1;
    L_AMOUNT := DBMS_LOB.GETLENGTH(L_BLOB);
    DBMS_LOB.CONVERTTOCLOB(L_CLOB,
    L_BLOB,
    L_AMOUNT,
    L_SRC_OFFSET,
    L_DEST_OFFSET,
    1,
    V_LANG_CONTEXT,
    L_WARNING);
    RETURN L_CLOB;
    END;
    And now, for the piece de' resistance, we need a BLOB to CLOB conversion that assumes that the BLOB data is stored initially in WE8ISO8859P1.
    To find correct CSID for WE8ISO8859P1, we can use this query:
    select nls_charset_id('WE8ISO8859P1') from dual;
    Gives "31"
    create or replace FUNCTION BLOB2CLOBASC(L_BLOB BLOB) RETURN CLOB IS
    L_CLOB CLOB;
    L_SRC_OFFSET NUMBER;
    L_DEST_OFFSET NUMBER;
    L_BLOB_CSID NUMBER := 31;      -- treat blob as  WE8ISO8859P1
    V_LANG_CONTEXT NUMBER := 31;   -- treat resulting clob as  WE8ISO8850P1
    L_WARNING NUMBER;
    L_AMOUNT NUMBER;
    BEGIN
    DBMS_LOB.CREATETEMPORARY(L_CLOB, TRUE);
    L_SRC_OFFSET := 1;
    L_DEST_OFFSET := 1;
    L_AMOUNT := DBMS_LOB.GETLENGTH(L_BLOB);
    DBMS_LOB.CONVERTTOCLOB(L_CLOB,
    L_BLOB,
    L_AMOUNT,
    L_SRC_OFFSET,
    L_DEST_OFFSET,
    L_BLOB_CSID,
    V_LANG_CONTEXT,
    L_WARNING);
    RETURN L_CLOB;
    END;
    select dump(dbms_lob.substr(blob2clobasc(data),4000,1)) from my_contents_lob;
    Now, we can compare these:
    select dbms_lob.compare(blob2clob(old.data),new.data) from  my_contents new,my_contents_lob old where new.pk1=old.pk1;
    DBMS_LOB.COMPARE(BLOB2CLOB(OLD.DATA),NEW.DATA)
                                                                 0
                                                                 0
                                                                 0
    Vs
    select dbms_lob.compare(blob2clobasc(old.data),new.data) from  my_contents new,my_contents_lob old where new.pk1=old.pk1;
    DBMS_LOB.COMPARE(BLOB2CLOBASC(OLD.DATA),NEW.DATA)
                                                                   -1
                                                                   -1
                                                                   -1
    update my_contents a set data=(select blob2clobasc(data) from my_contents_lob b where a.pk1= b.pk1)
        where pk1 in (select al.pk1 from my_contents_lob al where dbms_lob.compare(blob2clob(al.data),a.data) =0 );
    SQL> select dump(dbms_lob.substr(data,4000,1)) from my_contents where pk1 in (select pk1 from my_contents_lob);
    Confirms that we're now working properly.
    To run across all the _LOB tables we've created:
    [oracle@RESTORECLONE ~]$ exp file=all_fixed_lobs.dmp buffer=4000000 userid=my_user/mypass tables=MY_CONTENTS_LOB,MY_FORUM_LOB...
    [oracle@RESTORECLONE ~]$ scp all_fixed_lobs.dmp jboulier@PRODCLONE:/tmp
    And then on PRODCLONE we can import:
    imp file=all_fixed_lobs.dmp buffer=4000000 userid=system/XXXXXXX fromuser=my_user touser=my_user
    Instead of running the above update statement for all the affected tables, we can use a simple stored procedure:
    create or replace procedure fix_us7_CLOBS
      (TABLE_NAME varchar2,
         FIX_COL varchar2 )
        authid current_user
        as
         orig_sql varchar2(1000);
         bak_sql  varchar2(1000);
        begin
        dbms_output.put_line('Creating '||TABLE_NAME||'_PRECONV to preserve the original data in the table');
        bak_sql:='create table '||TABLE_NAME||'_preconv as select pk1,'||FIX_COL||' from '||TABLE_NAME||' where pk1 in (select pk1 from '||TABLE_NAME||'_LOB) ';
        execute immediate bak_sql;
        orig_sql:='update '||TABLE_NAME||' tabnew set '||FIX_COL||'= (select blob2clobasc ('||FIX_COL||') from '||TABLE_NAME||'_LOB taborig where tabnew.pk1=taborig.pk1)
       where pk1 in (
       select a.pk1 from '||TABLE_NAME||'_LOB a,'||TABLE_NAME||' b
          where a.pk1=b.pk1
                 and dbms_lob.compare(blob2clob(a.'||FIX_COL||'),b.'||FIX_COL||') = 0 )';
        -- dbms_output.put_line(orig_sql);
        execute immediate orig_sql;
       end;
    Now we can run the procedure and it fixes everything for our previously-broken tables, keeping the changed rows -- just in case -- in a table called table_name_PRECONV.
    set serveroutput on time on timing on;
    exec fix_us7_clobs('MY_CONTENTS','DATA');
    commit;
    After confirming with the client that the changes work -- and haven't noticeably broken anything else -- the same routines can be carefully run against the actual production database.

    We converted using the database using scripts I developed. I'm not quite sure how we converted is relevant, other than saying that we did not use the Oracle conversion utility (not csscan, but the GUI Java tool).
    A summary:
    1) We replaced the lossy characters by parsing a csscan output file
    2) After re-scanning with csscan and coming up clean, our DBA converted the database to AL32UTF8 (changed the parameter file, changing the character set, switched the semantics to char, etc).
    3) Final step was changing existing tables to use char semantics by changing the table schema for VARCHAR2 columns
    Any specific steps I cannot easily answer, I worked with a DBA at our company to do this work. I handled the character replacement / DDL changes and the DBA ran csscan & performed the database config changes.
    Our actual error message:
    ORA-31011: XML parsing failed
    ORA-19202: Error occurred in XML processing
    LPX-00210: expected '<' instead of '�Error at line 1
    31011. 00000 - "XML parsing failed"
    *Cause:    XML parser returned an error while trying to parse the document.
    *Action:   Check if the document to be parsed is valid.
    Error at Line: 24 Column: 15
    This seems to match the the document ID referenced below. I will ask our DBA to pull it up and review it.
    Please advise if more information is needed from my end.

Maybe you are looking for