728x90

14.10.xC6 버전부터 Round robin 방식으로 분할된 테이블의 개선된 기능을 소개드립니다.

Round robin 분할 방식로 구성된 테이블은 데이터가 지정된 DBspace를 순환하며 입력됩니다.

-- Round robin 분할 테이블에 데이터 입력
> create table test (a int) fragment by round robin in dbs1,dbs2;
Table created.
> insert into test select level from sysmaster:sysdual connect by level <= 5000;
5000 row(s) inserted.
-- 분할된 파티션 별 데이터 건수 확인
$ oncheck -pt demo:test | egrep 'partition|rows'
                  Table fragment partition dbs1 in DBspace dbs1
    Number of rows                 2500
                  Table fragment partition dbs1 in DBspace dbs2  
    Number of rows                 2500

위와 같은 상태에서 새로운 DBspace를 round robin 스키마에 추가하면, 기존 데이터는 이동하지 않고 새로 입력되는 데이터는 기존처럼 DBspace를 순환하며 입력됩니다.

-- Round robin 분할 테이블에 새로운 DBspace 추가
> alter fragment on table test add  dbs3;
Alter fragment completed.
> insert into test select level from sysmaster:sysdual connect by level <= 3;
3 row(s) inserted.
-- 분할된 파티션 별 데이터 건수 확인
$ oncheck -pt demo:test | egrep 'partition|rows'
                  Table fragment partition dbs1 in DBspace dbs1
    Number of rows                 2501
                  Table fragment partition dbs2 in DBspace dbs2
    Number of rows                 2501
                  Table fragment partition dbs3 in DBspace dbs3
    Number of rows                 1

14.10.xC6 버전부터는 Round robin 방식으로 구성된 테이블에 데이터가 입력될 경우, 가장 데이터 건수가 적은 파티션에 우선적으로 입력됩니다.

-- Round robin 분할 테이블에 데이터 입력
> create table test (a int) fragment by round robin in datadbs1,datadbs2;
Table created.
> insert into test select level from sysmaster:sysdual connect by level <= 5000;
5000 row(s) inserted.
-- Round robin 분할 테이블에 새로운 DBspace 추가
> alter fragment on table test add datadbs3;
Alter fragment completed.
> insert into test select level from sysmaster:sysdual connect by level <= 3;
3 row(s) inserted.
-- 분할된 파티션 별 데이터 건수 확인
$ oncheck -pt demo:test | egrep 'partition|rows'
                  Table fragment partition datadbs1 in DBspace datadbs1
    Number of rows                 2500
                  Table fragment partition datadbs2 in DBspace datadbs2
    Number of rows                 2500
                  Table fragment partition datadbs3 in DBspace datadbs3
    Number of rows                 3

 

파티션 별로 데이터량을 균등하게 유지하는 측면에서 좋은 기능인 것 같습니다. UPDATE 문장으로는 데이터가 이동하지 않더군요. 참고하시길 바랍니다.

 

728x90
728x90

최근에 공개된 Informix 14.10.xC6 버전에서 QUERY TIMEOUT 기능이 추가되었습니다.

아직 IBM Documentation에 설명된 내용이 없어서 며칠전에 있었던 Webinar의 내용을 참고해서 정리해보겠습니다.

 

QUERY TIMEOUT은 쿼리가 실행되는 시간을 제한하는 기능으로, OS 또는 DB 세션 환경 변수로 설정할 수 있습니다. onstat 명령에서 -g ses 과 -g sql 옵션을 사용하면 QUERY TIMEOUT 설정 값과 수행시간이 추가로 표시됩니다.

 

아래는 onstat -g sql의 출력결과입니다. Current SQL Statement 부분에만 표시됩니다. 기존에 보이는 내용에 추가로 QUERY_TIMEOUT setting과 Clock time elapsed 에 대한 정보가 표시되네요. QUERY_TIMEOUT 설정여부와 관계없이 항상 보입니다.

IBM Informix Dynamic Server Version 14.10.FC6 -- On-Line -- Up 3 days 22:36:44 -- 2664076 Kbytes
2021-06-26 09:00:13
Sess       SQL            Current            Iso Lock       SQL  ISAM F.E.
Id         Stmt type      Database           Lvl Mode       ERR  ERR  Vers  Explain
98         SELECT         stores_demo        CR  Not Wait   0    0    9.24  Off 
Current statement name : slctcur
Current SQL statement (3) :
  select * from systables, syscolumns, sysindexes
  QUERY_TIMEOUT setting: 00:00:20
  Clock time elapsed   : 00:00:15

위 내용은 QUERY_TIMEOUT을 20초로 설정한 예시인데, 쿼리 실행시간이 20초를 초과하면 아래와 같이 해당 문장이 중단됩니다. Ctrl + C 키를 누른 것과 동일한 효과입니다. 내부적으로 중단 처리 과정에서 설정된 값(20초)을 초과할 수 있다고 하네요.

...
levels           2
leaves           5.000000000000
nunique          113.0000000000
clust            10.00000000000
  213: Statement timed out or interrupted by user.
  157: ISAM error: Interrupted ISAM call
Error in line 1
Near character position 46

QUERY_TIMEOUT 설정은 아래와 같이 DML(update/insert/delete) 문장에는 적용되지 않네요.

설정된 시간을 초과해도 계속 수행됨을 알 수 있습니다.

IBM Informix Dynamic Server Version 14.10.FC6 -- On-Line -- Up 4 days 10:36:43 -- 2664076 Kbytes
2021-06-26 21:00:12
Sess       SQL            Current            Iso Lock       SQL  ISAM F.E.
Id         Stmt type      Database           Lvl Mode       ERR  ERR  Vers  Explain
106        SELECT INTO    sysmaster          CR  Not Wait   0    0    9.24  Off 
Current SQL statement (3) :
  select * from systabinfo, sysvplst, sysrawdsk into temp ttt
  QUERY_TIMEOUT setting: 00:00:20
  Clock time elapsed   : 00:02:25

 

공식적인 문서가 곧 나오겠지만, 현재까지 제가 확인한 바로는 QUERY_TIMEOUT 설정은 SELECT 문장에만 적용되는 것 같습니다. 잘못된 내용이나 추가로 확인한 부분에 대해서는 업데이트 하겠습니다.

 

728x90
728x90

안녕하세요. 오늘은 인포믹스의 AUTOLOCATE 기능에 대해 정리해보겠습니다.

인포믹스 12.10.xC3 버전부터 AUTOLOCATE라는 기능을 제공합니다. 이 기능은 테이블이나 인덱스의 배치 및 분할(fragmentation)을 자동화할 수 있습니다.

 

분할방식은 라운드 로빈(round-robin)으로 이뤄지고 AUTOLOCATE에 지정한 값의 수만큼 분할(fragment)이 생성됩니다.

인덱스의 경우는 라운드 로빈 방식으로 구성될 수 없으므로 적절한 페이지 크기의 단일 dbspace에 배치됩니다.

 

 

AUTOLOCATE 기능으로 테이블이나 인덱스가 배치될때 기본적으로는 모든 dbspace를 사용하는데, 사용자가 저장될 dbspace를 지정할 수도 있습니다. sysadmin 데이터베이스의 프로시저를 사용하여 autolocate database 옵션을 사용하면 됩니다. 지정한 dbspace 목록은 sysautolocate 카탈로그 테이블에서 확인할 수 있습니다.

 

사족으로 sysautolocate는 sysmaster 데이터베이스가 아닌 지정한 데이터베이스 별로 확인해야합니다. 저도 오늘에야 알게된 사실인데 IBM Community의 Benjamin Thompson의 답변으로 확인을 했습니다.

$ onmode -wf AUTOLOCATE=3
Value for AUTOLOCATE (3) was saved in config file.
Value of AUTOLOCATE has been changed to 3.
$ export DB_LOCALE=ko_kr.ksc
$ export CLIENT_LOCALE=ko_kr.ksc
$ dbaccess sysadmin -
Database selected.
> EXECUTE FUNCTION task("create database","demo","datadbs1","ko_kr.ksc");
(expression) Database demo created
1 row(s) retrieved.
> EXECUTE FUNCTION task("autolocate database", "demo", "datadbs1,datadbs2");
(expression) OK
$ echo "select dbsnum,dbsname[1,10],pagesize,flags from sysautolocate" | dbaccess demo
Database selected.
     dbsnum dbsname    pagesize       flags
          5 datadbs2       2048           1
          0 *                 0           2
          4 datadbs1       2048           1

위와 같이 설정한 상태에서 특정 테이블을 생성해보면 아래와 같이 datadbs1, datadbs2 두개의 dbspace에 자동으로 분할되어 생성된 것을 확인할 수 있습니다.

$ dbaccess demo -
Database selected.
> create table test (a int);
Table created.
$ dbschema -d demo -t test -ss
DBSCHEMA Schema Utility       INFORMIX-SQL Version 14.10.FC5
{ TABLE "informix".test row size = 4 number of columns = 1 index size = 0 }
create table "informix".test
  (
    a integer
  )
  fragment by round robin partition datadbs1_1 in datadbs1, partition datadbs2_2
    in datadbs2, partition datadbs1_3 in datadbs1
  extent size 8 next size 16 lock mode row;

최근에는 이런 기능들을 활용해서 일반 테이블은 AUTOLOCATE 설정을 따르게 하고, 대용량 테이블의 경우는 INTERVAL에 의한 분할 방식으로 구성하려고 하는 편입니다.

 

 

https://www.ibm.com/docs/en/informix-servers/14.10?topic=parameters-autolocate-configuration-parameter

 

728x90
728x90

Troubleshooting is a systematic approach to solving a problem. The goal of troubleshooting is to determine why something does not work as expected and how to resolve the problem. Certain common techniques can help with the task of troubleshooting.

The first step in the troubleshooting process is to describe the problem completely. Problem descriptions help you and the IBM® technical-support representative know where to start to find the cause of the problem. This step includes asking yourself basic questions:

  • What are the symptoms of the problem?
  • Where does the problem occur?
  • When does the problem occur?
  • Under which conditions does the problem occur?
  • Can the problem be reproduced?

The answers to these questions typically lead to a good description of the problem, which can then lead you to a problem resolution.

What are the symptoms of the problem?

When starting to describe a problem, the most obvious question is "What is the problem?" This question might seem straightforward; however, you can break it down into several more-focused questions that create a more descriptive picture of the problem. These questions can include:

  • Who, or what, is reporting the problem?
  • What are the error codes and messages?
  • How does the system fail? For example, is it a loop, hang, crash, performance degradation, or incorrect result?

Where does the problem occur?

Determining where the problem originates is not always easy, but it is one of the most important steps in resolving a problem. Many layers of technology can exist between the reporting and failing components. Networks, disks, and drivers are only a few of the components to consider when you are investigating problems.

The following questions help you to focus on where the problem occurs to isolate the problem layer:

  • Is the problem specific to one platform or operating system, or is it common across multiple platforms or operating systems?
  • Is the current environment and configuration supported?
  • Do all users have the problem?
  • (For multi-site installations.) Do all sites have the problem?

If one layer reports the problem, the problem does not necessarily originate in that layer. Part of identifying where a problem originates is understanding the environment in which it exists. Take some time to completely describe the problem environment, including the operating system and version, all corresponding software and versions, and hardware information. Confirm that you are running within an environment that is a supported configuration; many problems can be traced back to incompatible levels of software that are not intended to run together or have not been fully tested together.

When does the problem occur?

Develop a detailed timeline of events leading up to a failure, especially for those cases that are one-time occurrences. You can most easily develop a timeline by working backward: Start at the time an error was reported (as precisely as possible, even down to the millisecond), and work backward through the available logs and information. Typically, you need to look only as far as the first suspicious event that you find in a diagnostic log.

To develop a detailed timeline of events, answer these questions:

  • Does the problem happen only at a certain time of day or night?
  • How often does the problem happen?
  • What sequence of events leads up to the time that the problem is reported?
  • Does the problem happen after an environment change, such as upgrading or installing software or hardware?

Responding to these types of questions can give you a frame of reference in which to investigate the problem.

Under which conditions does the problem occur?

Knowing which systems and applications are running at the time that a problem occurs is an important part of troubleshooting. These questions about your environment can help you to identify the root cause of the problem:

  • Does the problem always occur when the same task is being performed?
  • Does a certain sequence of events need to happen for the problem to occur?
  • Do any other applications fail at the same time?

Answering these types of questions can help you explain the environment in which the problem occurs and correlate any dependencies. Remember that just because multiple problems might have occurred around the same time, the problems are not necessarily related.

Can the problem be reproduced?

From a troubleshooting standpoint, the ideal problem is one that can be reproduced. Typically, when a problem can be reproduced you have a larger set of tools or procedures at your disposal to help you investigate. Consequently, problems that you can reproduce are often easier to debug and solve.

However, problems that you can reproduce can have a disadvantage: If the problem is of significant business impact, you do not want it to recur. If possible, re-create the problem in a test or development environment, which typically offers you more flexibility and control during your investigation.

  • Can the problem be re-created on a test system?
  • Are multiple users or applications encountering the same type of problem?
  • Can the problem be re-created by running a single command, a set of commands, or a particular application?

출처 : https://www.ibm.com/docs/en/informix-servers/12.10?topic=support-techniques-troubleshooting-problems

728x90
728x90

You can perform routine administrative tasks that can prevent assertion failures or help prepare for recovering from assertion failures.

To prevent assertion failures on Informix®, perform the following tasks regularly:

Table 1. Preventing assertion failuresPrevention taskPurpose

Test your applications thoroughly in a realistic environment before releasing your applications into production. Applications can trigger assertion failures.Make sure that you have allocated enough resources: for example, physical and logical logs and shared memory.
Check and repair the consistency of your data.Run the following oncheck commands to check your system:
  • oncheck -cD: Data pages
  • oncheck -cI: Index pages
  • oncheck -cr: Reserved pages
  • oncheck -ce: Chunk-free list
  • oncheck -cc: System catalog tables
  • oncheck -pe: Physical information about chunks
Diagnosing and repairing consistency problems quickly can prevent major problems like data loss and assertion failures.
Upgrade to the latest major and fix pack release. Assertion failures can be caused by product defects. You can avoid many product defects by upgrading to the most current release.
Update statistics.When you change a table or indexing schema, update statistics to update the dictionary cache. By default, statistics are updated automatically by the Scheduler. You can customize automatic statistics updating for your system. Queries that use stale statistics can use too many resources and cause assertion failures. Stale statistics can also have a negative affect on query performance.Always update statistics after upgrading.

To prepare for assertion failures on Informix, perform the following tasks regularly:

Table 2. Preparing for assertion failuresPreparation taskPurpose

Back up your data and logical logs.You can use the ON-Bar utility or the ontape utility to back up your data and logical logs. The ON-Bar utility requires a storage manager. If data loss occurs, you can recover your data and recent transactions.
Back up your database and storage space schema information.Run the following commands to back up your schema information:
  • dbschema -ss -d database_name > dbschema_ss_database_name.out: Saves the schema information about the specified database in a file.
  • dbschema -c > dbschema_c.out: Saves the commands to reproduce storage spaces, chunks, physical logs, and logical logs in a file.
In a catastrophic failure, you can recreate your system.

 

출처 : https://www.ibm.com/docs/en/informix-servers/14.10?topic=failures-prevent-prepare-assertion

728x90
728x90

얼마전에 고객사 인포믹스에서 243 오류(Could not position within a table table-name)가 발생해서 onmode -I 명령으로 동일한 오류가 발생했을 때 진단 정보를 수집하도록 설정해두었습니다. 

 

그런데 진단 정보를 수집하는 설정 상태를 확인하는 방법이 있는지 알고싶어 IBM Community에 질문 글을 썼습니다.

onmode -I 명령을 수행하면 아래와 같이 인포믹스 온라인 로그에 메시지가 표시되기는 하지만 현재 설정되었는지 여부를 확인하는 방법을 알고 싶었습니다.

11:55:15  Verbose error trapping set, errno = 243, session_id = -1

 

질문 글을 올리고 금방 답변을 받았는데.. onstat 명령에 숨겨진 옵션이 있더군요.

$ onmode -I 243
$ onstat -g ras
IBM Informix Dynamic Server Version 11.70.FC9 -- On-Line -- Up 01:07:23 -- 23486904 Kbytes
 Diagnostics           Current Settings
 AFCRASH               0x00002481
 AFFAIL                0x00000401
 AFWARN                0x00000401
 AFDEBUG               0
 AFLINES               0
 BLOCKTIMEOUT          3600
 Block Status          Unblocked
 CCFLAGS               0x00000000
 CCFLAGS2              0x00000200
 DUMPCORE              0
 DUMPGCORE             0
 DUMPSHMEM             1
 DUMPCNT               1
 DUMPDIR               /work1/informix/ids1150fc6/tmp
 RHEAD_T               0x00000000541c3800
 SYSALARMPROGRAM       /work1/informix/ids1150fc6/etc/evidence.sh
 LTXHWM                70%
 LTXEHWM               80%
 DYNAMIC_LOGS          2
Traperror info:
 Errno          Session(s)
 243            All

onstat -g ras 명령의 출력 결과입니다. -g ras 옵션은 onstat 도움말과 IBM의 매뉴얼에 설명되지 않은 숨겨진 옵션입니다. 결과의 Traperror info 부분에서 현재 에러번호(Errno)와 특정 세션번호에 대해 진단 정보를 수집하도록 설정되어 있음을 확인할 수 있습니다.

728x90
728x90

Informix 서비스가 온라인 상태에서 어떻게 백업이 수행되는지 조사해봤습니다. 오랜기간 Informix를 경험했으면서도 아직도 내부 아키텍처에 정확히 알지 못하고 있었네요.

 

Informix 데이터베이스가 동시에 여러 트랜잭션에 의해 변경되는 중에도 백업을 수행할 수 있는 이유는 Physical Log가 있기 때문입니다. 백업을 시작한 이후부터 데이터가 저장된 청크의 페이지에 변경이 일어나면, 변경된 데이터의 기존 이미지(before-images)를 Physical Log에 기록합니다. 그리고 다시 temp table에 before-images를 복사하여 최종적으로는 백업 미디어(tape)에 기록한다고 하네요. 아래는 그 내용을 도식화한 그림입니다.

 

Informix Dynamic Server Internal Architecture and Advanced Administration - On-Line Archives and Log Backups

백업이 시작된 이후부터는 데이터 청크의 변경된 페이지는 무시합니다. before image를 가지고 있고 최종적으로는 Logical Log로 복구하기 때문이겠죠? 그리고 tape은 연속적으로 기록되어야하므로, before image는 백업 수행 도중에 기록되는 것 같습니다.

 

백업 수행중에 데이터를 변경할 때, before image가 temp table로 생성되는지 간단한 테스트를 해봤습니다.

ontape 백업이 실행중인 상태에서, 데이터를 증식하여 입력해보니 temporary dbspace에 temp table이 생기는 것을 확인할 수 있었습니다.

$ cat q1.sql
insert into customer_copy select * from customer connect by level < 6;
insert into customer_copy select * from customer connect by level < 7;
insert into customer_copy select * from customer connect by level < 8;
$ nohup dbaccess stores_demo q1.sql &
$ oncheck -pe tempdbs1
DBspace Usage Report: tempdbs1            Owner: informix  Created: 07/03/2013
 Chunk Pathname                             Pagesize(k)  Size(p)  Used(p)  Free(p)
     3 /informix/dbspace/tempdbs1                     4   250000   131125   118875
 Description                                                   Offset(p)  Size(p)
 ------------------------------------------------------------- -------- --------
 RESERVED PAGES                                                       0        2
 CHUNK FREELIST PAGE                                                  2        1
 (0x300001) tempdbs1:'informix'.TBLSpace                              3       50
 (0x300002) stores_demo:'informix'._temptable                        53   131072
 FREE                                                            131125   118875

해당 temp table(_temptable)은 트랜잭션이 종료되면 oncheck 명령으로 보았을 때 사라지는 걸로 봐선 곧바로 백업 파일에 기록되는 것 같습니다. temp dbspace 공간이 부족해서 백업이 실패하는 경우도 간혹 있으니 참고하세요~

728x90
728x90

인포믹스에서 함수 인덱스를 찾는 방법에 대한 질문이 있어서 찾아보았습니다.

우선 카탈로그 테이블인 sysindexes 부터 살펴보니 함수 인덱스임을 표시하는 컬럼은 없었습니다.

그래서 sysindexes 테이블의 함수 인덱스 정보가 다른 인덱스와 차이가 있는지 확인해봤습니다.

 

먼저 테이블과 함수 인덱스를 만들었습니다. 내용은 IBM 문서를 참고했습니다.

www.ibm.com/developerworks/data/library/techarticle/dm-0712wilcox/index.html

$ dbaccess stores_demo -
Database selected.
> CREATE TABLE circles ( radius FLOAT );
Table created.
> CREATE FUNCTION circleArea( radius FLOAT ) RETURNS float
>     WITH (NOT VARIANT);
>
>     RETURN 3.14159 * radius * radius;
> END FUNCTION;
Routine created.
> CREATE INDEX areaOfCircleIndex on circles( circleArea( radius ) );
Index created.

 

해당 인덱스에 대한 sysindexes 테이블의 정보를 확인해보았습니다.

> select * from sysindexes where idxname='areaofcircleindex';
idxname    areaofcircleindex
owner      informix
tabid      162
idxtype    D
clustered
part1      0
part2      0
part3      0
part4      0
part5      0
part6      0
part7      0
part8      0
part9      0
part10     0
part11     0
part12     0
part13     0
part14     0
part15     0
part16     0
levels     1
leaves     1.000000000000
nunique    0.00
clust      0.00
1 row(s) retrieved.

특이하게도 일반 인덱스와 달리 part1 값이 0으로 표시됩니다. 인덱스를 만들 때 컬럼 순서를 바꾸고 일반 컬럼과 혼용해도 동일한 결과를 보여줍니다. 그럼 part1 값이 0이면 함수 인덱스인가? 라는 생각이 들어서 정말 그런지 실행해보았습니다.

> select owner, idxname from sysindexes where tabid > 99 and idxname[1,1] <> ' ' and part1 = 0;
owner    informix
idxname  ucnameindex
owner    informix
idxname  ts_data_location_spix
owner    informix
idxname  areaofcircleindex
3 row(s) retrieved.

 

데모용 데이터베이스인 stores_demo에서 수행해보니 opclass에 대한 인덱스와 함수 인덱스 두개가 보입니다. 정확히 함수 인덱스만 나오는 것은 아니고 일반적인 타입의 인덱스는 제외되는 것 같습니다. 어설프지만 확인은 가능하네요.

그래서 좀 더 정확한 방법에 대한 조언을 구하기위해 IBM Community에 질문을 올렸습니다. 바로 Art Kagel씨와 Paul Watson씨가 명쾌한 답을 주시는군요. 답은 sysindices 카탈로그 테이블에 있었습니다.

> select idxname from sysindices where indexkeys::lvarchar matches '*<[0-9]*>*';
idxname  ucnameindex
idxname  areaofcircleindex
2 row(s) retrieved.
> select idxname, indexkeys from sysindices where indexkeys::lvarchar matches '*<[0-9]*>*';
idxname    ucnameindex
indexkeys  2 [1], <1757>(3) [1], 1 [1]
idxname    areaofcircleindex
indexkeys  <1758>(1) [1]
2 row(s) retrieved.

sysindices 테이블의 indexkeys 컬럼 값에 함수 인덱스에 대한 정보가 있더군요. opclass에 대한 정보도 있는데 이부분은 저도 잘은 모르고 이 내용과는 벗어나는 내용이라 넘어가겠습니다. indexkeys 컬럼에도 딱 이 인덱스가 함수 인덱스다! 라고 알려주는 플래그 값이 있는건 아니지만, 함수 인덱스인 경우 <> 사이에 procid 값 정보가 있습니다. 이 정보로 인덱스가 함수 인덱스임을 알 수 있는 것입니다.

아래는 IBM Knowledge Center의 sysindices 테이블에 대한 설명입니다.


The fields within the indexkeys columns have the following significance:

  • The procid (as in sysprocedures) exists only for a functional index on return values of a function defined on columns of the table.
  • The list of columns (col1, col2, ... , coln) in the second field identifies the columns on which the index is defined. The maximum is language-dependent: up to 341 for an SPL or Java™ UDR; up to 102 for a C UDR.
  • The opclassid identifies the secondary access method that the database server used to build and to search the index. This is the same as the sysopclasses.opclassid value for the access method.
  •  

IBM Community에서 좋은 것을 배웠네요.

728x90
728x90

안녕하세요. 지난번에 이어 Informix에서 Oracle 데이터베이스 참조하기 위한 구성을 테스트해봤습니다.

마찬가지로 Enterprise Gateway Manager를 사용했습니다. 그런데 Informix 데이터베이스에 접속한 상태에서 Oracle 데이터베이스를 참조하려고 하니 908 오류가 발생하면서 접속이 되지 않더군요. 그래서 이번에는 EGM 7.31.UD3 버전으로 테스트를 시도해봤습니다.

 

1. 테스트 환경

① O/S : CentOS 7

② 클라이언트 : Informix Server 12.10, Informix Server 14.10

③ 접속 대상 : Oracle 11gR2, SQL Server 2017 on Linux

④ EGM 버전 : 7.31.UD3

 

2. 환경변수 설정

별도 EGM 인스턴스를 기동해야해서 INFORMIXSERVER, INFORMIXDIR을 수정했습니다.

Oracle을 사용하려는 경우 egmenv.sh 에서 ORACLE_HOME 환경변수를 지정하라고 합니다.

사실 ODBC를 사용하는 경우 tnsnames.ora 파일만 지정하면 되고 별도 라이브러리는 필요없으므로 ORACLE_HOME 설정이 되어있지 않어도 접속이 되었습니다. 따라서 오라클 클라이언트를 별도로 설치하지 않아도 됩니다. 이건 기본 테스트라 그렇지 설치가 필요한 경우도 있겠죠?

 

3. odbc.ini 파일 수정

EGM 7.31.UD4 버전의 ODBC 드라이버와 odbc.ini 파일을 참고하여 설정했습니다. 앞서 egmenv.sh 스크립트에서 ODBC 드라이버 매니저는 7.31.UD3의 라이브러리를 참조하도록 했습니다. (LD_LIBRARY_PATH=$INFORMIXDIR/egm/odbc/lib)

그리고 접속 대상인 Oracle 서버의 접속정보인 tnsnames.ora 파일의 경로를 TNSNamesFile에 설정하면 됩니다.

[oracle]
Driver=/work1/informix/egm/egm/odbc/lib/IXora27.so
Description=DataDirect 7.1 Oracle
AlternateServers=
ApplicationUsingThreads=1
ArraySize=7.100
CatalogIncludesSynonyms=1
CatalogOptions=0
ClientVersion=9iR2
ConnectionRetryCount=0
ConnectionRetryDelay=3
DefaultLongDataBuffLen=1024
DescribeAtPrepare=0
EnableDescribeParam=0
EnableNcharSupport=0
EnableScrollableCursors=1
EnableStaticCursorsForLongData=0
EnableTimestampWithTimeZone=0
LoadBalancing=0
LocalTimeZoneOffset=
LockTimeOut=-1
LogonID=
OptimizeLongPerformance=0
Password=
ProcedureRetResults=0
ReportCodePageConversionErrors=0
ServerName=test
TimestampEscapeMapping=0
TNSNamesFile=/work1/informix/egm/tnsnames.ora
UseCurrentSchema=1

4. SQL 실행 테스트

Oracle의 샘플 스키마인 scott 계정의 emp테이블을 Informix 데이터베이스로 가져와봅니다.

$ export CLIENT_LOCALE=en_us.819
$ export DB_LOCALE=en_us.819
$ echo "create table emp as select * from oracle@egm731ud3:\"SCOTT\".emp" | dbaccess stores_demo
Database selected.
14 row(s) retrieved into table.
Database closed.
[informix@db2 1210FC12W1XC]$ echo "select * from emp" | dbaccess stores_demo
Database selected.
 empno ename      job          mgr hiredate                  sal      comm deptno
  7369 SMITH      CLERK       7902 1980-12-17 00:00:00    800.00               20
  7566 JONES      MANAGER     7839 1981-04-02 00:00:00   2975.00               21
  7782 CLARK      MANAGER     7839 1981-06-09 00:00:00   2450.00               11
  7844 TURNER     SALESMAN    7698 1981-09-08 00:00:00   1500.00      0.00     30
  7902 FORD       ANALYST     7566 1981-12-03 00:00:00   3000.00               20
  7499 ALLEN      SALESMAN    7698 1981-02-20 00:00:00   1600.00    300.00     30
  7654 MARTIN     SALESMAN    7698 1981-09-28 00:00:00   1250.00   1400.00     30
  7788 SCOTT      ANALYST     7566 1987-04-19 00:00:00   3000.00               20
  7876 ADAMS      CLERK       7788 1987-05-23 00:00:00   1100.00               20
  7934 MILLER     CLERK       7782 1982-01-23 00:00:00   1300.00               10
  7521 WARD       SALESMAN    7698 1981-02-22 00:00:00   1250.00    500.00     30
  7698 BLAKE      MANAGER     7839 1981-05-01 00:00:00   2850.00               31
  7839 KING       PRESIDENT        1981-11-17 00:00:00   5000.00               10
  7900 JAMES      CLERK       7698 1981-12-03 00:00:00    950.00               31

Informix와 Oracle 테이블간의 inner join도 실행해보고 실행계획도 확인해봤습니다. 이것 참 재미있네요. Informix 테이블에 대한 정보만 표시되고 Oracle의 테이블에 대해서는 REMOTE PATH로 표시되네요.

$ echo "set explain on ;select b.* from emp a, oracle@egm731ud3:\"SCOTT\".emp b where a.empno = b.empno and a.empno = 7369" | dbaccess stores_demo
Database selected.
Explain set.
 empno ename      job          mgr hiredate                  sal      comm deptno
  7369 SMITH      CLERK       7902 1980-12-17 00:00:00    800.00               20
1 row(s) retrieved.
Database closed.
$  cat sqexplain.out
QUERY: (OPTIMIZATION TIMESTAMP: 09-14-2020 17:33:20)
------
select b.* from emp a, oracle@egm731ud3:"SCOTT".emp b where a.empno = b.empno and a.empno = 7369
Estimated Cost: 6
Estimated # of Rows Returned: 1
  1) informix.a: SEQUENTIAL SCAN  (Serial, fragments: ALL)
  2) informix.b: REMOTE PATH
    REMOTE SESSION ID FOR 'egm731ud3' is UNKNOWN
    Remote SQL Request:
    select x0.empno ,x0.ename ,x0.job ,x0.mgr ,x0.hiredate ,x0.sal ,x0.comm ,x0.deptno from oracle:"SCOTT".emp x0 where ((? = x0.empno ) AND (x0.empno = 7369 ) )                            
NESTED LOOP JOIN
Query statistics:
-----------------
  Table map :
  ----------------------------
  Internal name     Table name
  ----------------------------
  t1                a
  type     table  rows_prod  est_rows  rows_scan  time       est_cost
  -------------------------------------------------------------------
  scan     t1     14         1         14         00:00.00   4
  type     rows_prod  est_rows  time       est_cost
  -------------------------------------------------
  remote   1          1         00:00.01   0
  type     rows_prod  est_rows  time       est_cost
  -------------------------------------------------
  nljoin   1          1         00:00.01   7

SQL Server의 경우도 inner join이 잘 실행되었습니다. 테스트 환경이라 ODBC 라이브러리가 꼬인건지 모르겠지만.. 실행이 되는건 확인했네요. ODBC 드라이버 매니저와 드라이버가 적절하게 구성되는 것이 제일 중요한 것 같습니다. 인터넷에서 문서들을 찾다보면 unixODBC와 각 데이터베이스에서 제공되는 ODBC 드라이버로 구성한 사례들도 있는데 저는 라이브러리를 새로 컴파일하기가 귀찮아서 기본으로 제공되는 라이브러리들로 테스트했습니다. 깔끔한 상태의 컴퓨터에서 테스트해보시길 권장드립니다.

728x90
728x90

안녕하세요. Informix는 기본적으로 Informix간의 데이터베이스 상호 참조는 가능하지만, 이기종 데이터베이스를 참조하는 기능은 없습니다. 이기종 데이터베이스를 참조하려면 Informix Enterprise Gateway Manager(EGM)가 필요한데요. EGM은 아래 그림과 같이 Informix Server와 별도의 프로세스를 거쳐서 이기종 데이터베이스에 접근할 수 있도록 해줍니다.

 

Informix High-Performance Federated Database System (Yunming Wang, 2012 IIUG Conference)

Enterprise Gateway는 DRDA 프로토콜과 ODBC를 사용하는 두가지 제품군이 있습니다. DRDA 프로토콜로는 DB2/zos와 UDB에, ODBC로는 DataDirect 사에서 제공하는 ODBC 관리자 및 드라이버를 통해 Oracle, SQL Server, MySQL 등의 데이터베이스에 접근할 수 있습니다. 한가지 주의할 점은 32비트 ODBC 관리자를 사용하므로 DataDirect에서 제공되지 않는 ODBC 드라이버를 사용할 경우 32비트용으로 사용해야한다는 하는 점입니다.

저는 EGM 7.31.UD4 버전을 설치하고 SQL Server에 접속하는 테스트를 해보았습니다. 시행착오가 좀 있었는데 구성 자체는 어렵지 않았습니다.

 

1. EGM 설치환경

① O/S : CentOS 7

② 클라이언트 : Informix Server 14.10.FC4W1

③ 접속대상DB : SQL Server 2017 on Linux

 

클라이언트와 접속대상DB가 같은 호스트에 있는 상태에서 구성 및 테스트를 했습니다.

 

2. EGM 구성순서

① EGM 설치 

설치전에 INFORMIXDIR 설정이 필요하고, 설치는 root 계정으로 합니다.

② EGM 인스턴스의 sqlhosts 파일 작성

Informix Server와 동일한 형식의 sqlhosts 파일을 작성합니다. 위치는 $INFORMIXDIR/etc 입니다.

③ EGM 환경변수 파일 수정

INFORMIXSERVER와 LD_LIBRARY 환경변수 설정의 주석을 제거하고 필요한 경우 라이브러리 경로를 추가합니다.

egmdba 유틸리티를 사용하려면 INFORMIXTERM 환경변수도 설정하는 것이 좋습니다.

그리고 GWDIRECTMODE를 설정해야 dbaccess 같은 유틸리티에서 직접 이기종 데이터베이스에 접속할 수 있습니다.

관련 내용은 아래 링크에서 확인했습니다.

members.iiug.org/forums/ids/index.cgi/read/23480

www.ibm.com/support/pages/error-29080-when-trying-use-substr-function-oracle-database

④ odbc.ini 파일 수정

$INFORMIXDIR/egm/odbc 경로에 odbc.ini 파일이 있습니다. 이 파일에서 SQL Server에 접속 정보를 수정하거나 추가합니다. 수정할 경우 Address와 dbname만 수정하면 됩니다.

[mssql]
Driver=/work1/informix/egm/egm/odbc/lib/IXsqls28.so
Description=DataDirect 8.0 SQL Server Wire Protocol
Address=xxx.xx.xx.xx,1433
AlternateServers=
AnsiNPW=Yes
ConnectionRetryCount=0
ConnectionRetryDelay=3
Database=dbname
LoadBalancing=0
LogonID=
Password=
QuotedId=No
SnapshotSerializable=0

3. EGM 프로세스 실행

EGM은 root 계정으로만 실행 가능합니다. root가 아닌 계정으로 실행하면 아래와 같이 오류가 발생합니다.

[informix@db2 odbc]$ egmd egm731ud4 -s egm -l /work1/informix/egm/egmd.log
2020-09-11 11:10:37.916976 daemon err = 25501: oserr = 0: errstr =  : The sqlexecd daemon must be started by root.

4. EGM 유저 및 데이터소스 등록

egmdba 유틸리티를 사용하여 EGM에서 사용할 유저명과 ODBC 데이터소스 이름, 데이터 소스에 접속하기위한 정보를 등록합니다. egmdba는 root 계정으로도 실행할 수 있지만 전체 관리 기능을 사용하려면 informix 계정으로 실행해야 합니다.

5. 접속 테스트

dbaccess를 사용하여 접속 테스트를 해봅니다. 

6. Informix의 데이터베이스에 접속한 상태에서 SQL Server 데이터베이스의 테이블을 조회하려고 할 때는, 아래처럼 오류가 발생하면서 EGM 프로세스가 다운되었습니다. 이 부분은 좀 더 테스트를 해봐야할 것 같습니다.

이기종 데이터베이스에 접근하는 것은 상당히 좋은 기능이지만 EGM은 별도의 상용제품이기 때문에 구매를 해야합니다. 따라서 기업입장에서는 비용을 들여서 구축하기에는 다소 부담이 될 것 같습니다.

시간나는대로 Oracle이나 MySQL도 접속 테스트를 해봐야겠습니다.

728x90

+ Recent posts