저자: Jonathan Gennick
새로운 SQL/XML 함수는 관계형 데이타와 XML을 표준에 기반하여 연결합니다.
수 십년 동안 기업들은 관계형 데이타베이스에 데이타를 쏟아 부어 왔습니다. 그러나 다른 기업과 데이타를 교환하는 기업들은 관계형 데이타베이스에서 데이타를 꺼내 이를 XML 포맷으로 변경한 후 비즈니스 파트너에게 전송해야 하는 경우가 갈수록 늘어나고 있습니다.
SQL/XML 표준
Oracle9i Database에는 관계형 데이타를 쿼리하고 XML 문서를 반환할 수 있는 여러 표준 기반 함수들이 들어 있습니다. 이 함수들을 통칭하여 SQL/XML이라 하며 때때로 SQLX라고 불리기도 합니다. SQL/XML은 현재 ANSI/ISO SQL 표준의 일부(정확히 말해 Part 14)로 등장하고 있으며 올해 후반 ISO/IEC 표준으로 발표될 예정입니다. SQL/XML 표준은 업계의 폭 넓은 지원을 받고 있으며, SQL/XML 표준 정의 작업과 관련된 주요 데이타베이스 업체들로는 IBM, Microsoft, Oracle, Sybase 등이 있습니다.
SQL/XML 국제 표준 최종안(The Final Draft International Standard for SQL/XML)에서는 다음과 같은 요소들을 정의하고 있습니다.
XML: XML 데이타를 담는 데이타 유형
XMLAgg: GROUP BY 질의에서 XML 데이타를 그룹으로 분류 또는 집계하는 함수
XMLAttributes: SQL 질의에 의해 반환된 XML 요소에 특성을 설정하는 데 사용되는 함수
XMLConcat: 둘 이상의 XML 값을 연결하는 함수
XMLElement: 관계형 값을 XML 요소로 변형시키는 함수(형식: <elementName>value</elementName>)
XMLForest: 관계형 값 목록으로부터 XML 요소의 목록(일명: `포리스트(forest)`)을 생성하는 함수
XMLNamespaces: XML 요소에서 네임스페이스를 선언하는 함수
XMLSerialize: XML 값을 문자열로 직렬화하는 함수
이 목록으로부터 Oracle9i Database는 XML 데이타 유형(XMLType), XMLAgg, XMLConcat, XMLElement 및 XMLForest 등을 구현합니다. 향후 출시되는 버전에서는 추가로 다른 함수를 지원할 계획입니다.
함수와 데이타 유형 외에도 SQL/XML 표준에서는 열 이름을 XML 요소 이름으로 변환하고 SQL 데이타 유형을 XML 데이타 유형으로 변환하는 규칙을 정의합니다. 이 규칙들은 XMLElement 및 기타 SQL/XML 함수들에 의해 자동으로 적용됩니다.
XML 문서 생성
여러분이 관광 안내소에 근무하고 있으며, 관광객들의 관심을 끌만한 관광 명소에 대한 정보를 다음 테이블과 같이 관계형으로 저장하고 있다고 가정해 보십시오.
SQL> describe COUNTY
Name Null? Type
-------------- ----- --------------
COUNTY_NAME VARCHAR2(10)
STATE VARCHAR2(2)
SQL> describe ATTRACTION
Name Null? Type
-------------- ----- --------------
COUNTY_NAME VARCHAR2(10)
ATTRACTION_NAME VARCHAR2(30)
ATTRACTION_URL VARCHAR2(40)
GOVERNMENT_OWNED CHAR(1)
LOCATION VARCHAR2(20)
여러분은 방금 이 데이타를 다른 지역의 유사한 사무소로 보내 줄 것을 요청 받았습니다. 이 데이타를 보낼 때는 반드시 XML로 보내야 합니다. 우선 XMLElement를 활용하여 각 관광 명소에 대한 XML 요소를 다음과 같이 생성합니다.
SELECT XMLElement("Attraction",
attraction_name)
FROM attraction;
XMLELEMENT("ATTRACTION",ATTRACTION_NAME)
------------------------------------------
<Attraction>Pictured Rocks</Attraction>
<Attraction>Da Yoopers ... </Attraction>
<Attraction>Valley Camp ...</Attraction>
...
XMLElement는 확실히 이해해야 할 가장 중요한 SQL/XML 기능 중의 하나인 것은 XML 요소 생성이야말로 SQL/XML이 존재하는 근본적인 이유이기 때문입니다. XMLElement의 첫 번째 인수는 문자열 인수가 아니라 식별자로서 테이블 이름 또는 열 이름이 식별자인 것과 같은 의미입니다. 그래서 위의 XMLElement 질의에서 이중 따옴표를 사용했습니다. 테이블에서 소문자 열 이름을 사용하려면 테이블을 생성할 때 그 열 이름에 이중 따옴표를 사용하십시오. 마찬가지로 요소 이름을 소문자로 하는 경우에도 이중 따옴표로 묶습니다. XMLElement에 대한 두 번째 인수는 현재 생성하고 있는 요소에 값을 제공하는 열 이름입니다.
이번 데이타 전달에는 관광 명소 이름 뿐만 아니라 다른 정보도 전달하려 합니다. 목록 1과 같이 XMLElement에 호출을 중첩하여 각각의 관광 명소에 하위 요소를 생성할 수 있습니다. XMLElement에 대한 외부 호출은 <Attraction> 요소를 생성합니다. XMLElement에 대한 내부 호출은 중첩된 <Name>, <Location>, <URL> 요소를 생성합니다. XMLAttributes를 외부 XMLElement 함수 호출의 둘째 인수로 사용하는 것에 유의하십시오. XMLAttributes의 호출은 XMLElements에 선택적으로 쓸 수 있는 둘째 인수이며 이 경우에는 각 <Attraction> 태그에서 볼 수 있는 GOV 특성이 만들어집니다.
XMLElement 함수가 문자열 값이 아니라 XMLType 값을 반환한다는 점을 이해하는 것이 중요합니다. 목록에 문자가 표시되는 것은 SQL*Plus(Oracle9i Release 2)가 여러분이 선택한 모든 XMLType 값에 대해 XML 텍스트를 암묵적으로 추출하여 표시하기 때문입니다. SQL*Plus를 사용하여 이 문서에서 그 예제를 재현해 보려면, 여기에서 테이블 생성 스크립트를 다운로드하십시오. SQL*Plus에서는 XML 출력이 절단되지 않도록 SET LONG 2000 명령을 내리고, 선택적으로 SET PAGESIZE 80 명령을 내려 XML 출력에 성가신 페이지 구분이 생기지 않도록 합니다.
Null 요소의 처리
관계형 데이타를 다룰 때는 null 값이 나타날 가능성을 반드시 고려해야 합니다. 예를 들어 LOCATION 열이 일부 관광 명소에 대해 null인 경우에는 어떨까요? XMLElement을 사용하는 경우 null 열 값은 목록 2의 첫번째 질의와 결과에 나타난 바와 같이 빈 요소로 나타납니다. XML에 이러한 빈 요소를 두고 싶지 않다면 최소한 두 가지 해결책이 있습니다.
빈 XML 요소 생성을 방지하는 데 사용할 수 있는 방법 중 하나는 SQL CASE 표현식을 사용하여 열의 null 값을 테스트하고 null 또는 XMLElement의 결과를 반환하는 것입니다. 목록 2의 둘째 질의가 이 방법을 구현한 것입니다. 문제의 열이 null인 경우 각 CASE 표현식 결과는 항상 null이며, 내부 XMLElement 함수에 null이 아닌 값을 전달합니다. 외부 XMLElement은 null이 아닌 모든 값을 끌어모으며 빈 XML 요소가 될 모든 null은 무시됩니다.
빈 XML 요소 생성을 방지하는 또 다른 방법은 XMLForest 함수를 사용하는 것입니다. XML에서는 <Attraction> 아래 중첩된 요소들을 "포리스트(forest)"라 부릅니다. XMLForest를 이용하면 단 하나의 함수 호출을 가진 요소의 포리스트(forest)를 생성할 수 있습니다. 이러한 요소를 생성할 때 XMLForest는 null 값을 가진 요소들은 생략합니다. 이러한 결과를 다음 질의의 출력에서 볼 수 있습니다. 여기서 XMLForest는 질의 결과에서 null <location> 요소를 산출하지 않습니다.
SELECT XMLElement("Attraction",
XMLAttributes(government_owned AS GOV),
XMLForest(attraction_name AS "Name",
Location AS "Location",
attraction_url AS "URL"))
FROM attraction
WHERE attraction_name=`Mackinac Bridge`;
XMLELEMENT("ATTRACTION",XMLATTRIBUTES(GOV
-------------------------------------------------
<Attraction GOV="Y">
<Name>Mackinac Bridge</Name>
<URL>http://www.mackinacbridge.org/</URL>
</Attraction>
이 질의는 XMLForest에 한 번 호출하므로 목록 2에서와 같이 XMLElement에 세 번 호출하는 경우보다 입력하기 쉽고 입력 오류의 여지도 적습니다. 두 경우 모두, 질의 결과에서 null 요소가 제거됩니다. XMLForest 사용의 단점은 요소 특성을 지정할 수 없다는 점입니다. 요소에 특성을 지정해야 한다면 반드시 XMLElement를 XMLAttributes와 함께 사용해야 합니다.
XML 요소의 집계
앞의 질의는 각 관광 명소마다 별도의 XML 문서를 생성했습니다. 이는 그다지 현실적인 시나리오는 아닙니다. 관광 명소에 대한 데이타를 비즈니스 파트너에게 제공하는 경우에는 어떤 식으로든 데이타를 집계하고자 할 것입니다. 예를 들어 한 나라의 모든 관광 명소를 한 데 모아 한 문서로 전송하고자 할 수도 있습니다. 이 경우에는 XMLAgg 함수를 GROUP BY 질의와 함께 사용하면 그렇게 할 수 있습니다.
XMLAgg는 MIN, MAX, AVG 등과 같은 집계 함수입니다. 이 함수 사용의 핵심은 어떤 같은 값에 따라 데이타를 그룹으로 묶는 것입니다. 목록 3에서 질의는 데이타를 나라 이름으로 묶습니다. 그러면 XMLAgg 함수는 해당 나라의 모든 개별 <Attraction> 요소들을 가져와 한 데 연결하여 단일한 XMLType 값으로 반환하고, 그 값은 <County> 요소를 생성하는 새로운 포함 XMLElement 함수 호출로 입력됩니다. 그 결과는 목록 3< county. per document XML one returns> 에서 확인 하실 수 있습니다. 목록 3에서 XMLAttributes이 여러 특성 값을 생성하는 데 사용되는 것을 보게 됩니다.
XMLAttributes에 대한 가장 바깥 쪽의 호출은 세 개의 특성 즉, 나라 이름에 대한 것 하나, 그리고 해당 문서가 따르는 XML 스키마를 가리키는 것 둘을 생성합니다. 여기서 질의는 GROUP BY이므로 가장 바깥 쪽의 XMLElement 함수 호출과 그와 연관된 XMLAttributes 호출은 요약된 열만을 참조할 수 있습니다. c.county_name 대신 a.county_name을 사용하면 오류가 나타나는데 이는 a.county_name이 GROUP BY 표현식이 아니기 때문입니다.
기타 아래의 내용도 한번 참고 해 보세요...
SQL/XML 표준 학습
http://www.sqlx.org
Oracle SQL/XML에 대한 상세 정보
http://www.oracle.com/otn.oracle.com/tech/xml/
http://www.oracle.com/xmldb/htdocs/sql_xml.html
이 문서의 테이블 생성 코드 다운로드
http://www.oracle.com/otn.oracle.com/oramag/oracle/03-may/o33xml_tablecreate.zip
XML DB 데모
http://www.oracle.com/otn.oracle.com/tech/xml/xmldb
관련 자료 읽기
http://www.oracle.com//kr/magazine/webcolumns/2003/o13xml.html
XML DB에 대하여
http://otn.oracle.co.kr/tech/xml
technet.oracle.co.kr에 있는 내용 입니다.
참고 하세요~
새로운 SQL/XML 함수는 관계형 데이타와 XML을 표준에 기반하여 연결합니다.
수 십년 동안 기업들은 관계형 데이타베이스에 데이타를 쏟아 부어 왔습니다. 그러나 다른 기업과 데이타를 교환하는 기업들은 관계형 데이타베이스에서 데이타를 꺼내 이를 XML 포맷으로 변경한 후 비즈니스 파트너에게 전송해야 하는 경우가 갈수록 늘어나고 있습니다.
SQL/XML 표준
Oracle9i Database에는 관계형 데이타를 쿼리하고 XML 문서를 반환할 수 있는 여러 표준 기반 함수들이 들어 있습니다. 이 함수들을 통칭하여 SQL/XML이라 하며 때때로 SQLX라고 불리기도 합니다. SQL/XML은 현재 ANSI/ISO SQL 표준의 일부(정확히 말해 Part 14)로 등장하고 있으며 올해 후반 ISO/IEC 표준으로 발표될 예정입니다. SQL/XML 표준은 업계의 폭 넓은 지원을 받고 있으며, SQL/XML 표준 정의 작업과 관련된 주요 데이타베이스 업체들로는 IBM, Microsoft, Oracle, Sybase 등이 있습니다.
SQL/XML 국제 표준 최종안(The Final Draft International Standard for SQL/XML)에서는 다음과 같은 요소들을 정의하고 있습니다.
XML: XML 데이타를 담는 데이타 유형
XMLAgg: GROUP BY 질의에서 XML 데이타를 그룹으로 분류 또는 집계하는 함수
XMLAttributes: SQL 질의에 의해 반환된 XML 요소에 특성을 설정하는 데 사용되는 함수
XMLConcat: 둘 이상의 XML 값을 연결하는 함수
XMLElement: 관계형 값을 XML 요소로 변형시키는 함수(형식: <elementName>value</elementName>)
XMLForest: 관계형 값 목록으로부터 XML 요소의 목록(일명: `포리스트(forest)`)을 생성하는 함수
XMLNamespaces: XML 요소에서 네임스페이스를 선언하는 함수
XMLSerialize: XML 값을 문자열로 직렬화하는 함수
이 목록으로부터 Oracle9i Database는 XML 데이타 유형(XMLType), XMLAgg, XMLConcat, XMLElement 및 XMLForest 등을 구현합니다. 향후 출시되는 버전에서는 추가로 다른 함수를 지원할 계획입니다.
함수와 데이타 유형 외에도 SQL/XML 표준에서는 열 이름을 XML 요소 이름으로 변환하고 SQL 데이타 유형을 XML 데이타 유형으로 변환하는 규칙을 정의합니다. 이 규칙들은 XMLElement 및 기타 SQL/XML 함수들에 의해 자동으로 적용됩니다.
XML 문서 생성
여러분이 관광 안내소에 근무하고 있으며, 관광객들의 관심을 끌만한 관광 명소에 대한 정보를 다음 테이블과 같이 관계형으로 저장하고 있다고 가정해 보십시오.
SQL> describe COUNTY
Name Null? Type
-------------- ----- --------------
COUNTY_NAME VARCHAR2(10)
STATE VARCHAR2(2)
SQL> describe ATTRACTION
Name Null? Type
-------------- ----- --------------
COUNTY_NAME VARCHAR2(10)
ATTRACTION_NAME VARCHAR2(30)
ATTRACTION_URL VARCHAR2(40)
GOVERNMENT_OWNED CHAR(1)
LOCATION VARCHAR2(20)
여러분은 방금 이 데이타를 다른 지역의 유사한 사무소로 보내 줄 것을 요청 받았습니다. 이 데이타를 보낼 때는 반드시 XML로 보내야 합니다. 우선 XMLElement를 활용하여 각 관광 명소에 대한 XML 요소를 다음과 같이 생성합니다.
SELECT XMLElement("Attraction",
attraction_name)
FROM attraction;
XMLELEMENT("ATTRACTION",ATTRACTION_NAME)
------------------------------------------
<Attraction>Pictured Rocks</Attraction>
<Attraction>Da Yoopers ... </Attraction>
<Attraction>Valley Camp ...</Attraction>
...
XMLElement는 확실히 이해해야 할 가장 중요한 SQL/XML 기능 중의 하나인 것은 XML 요소 생성이야말로 SQL/XML이 존재하는 근본적인 이유이기 때문입니다. XMLElement의 첫 번째 인수는 문자열 인수가 아니라 식별자로서 테이블 이름 또는 열 이름이 식별자인 것과 같은 의미입니다. 그래서 위의 XMLElement 질의에서 이중 따옴표를 사용했습니다. 테이블에서 소문자 열 이름을 사용하려면 테이블을 생성할 때 그 열 이름에 이중 따옴표를 사용하십시오. 마찬가지로 요소 이름을 소문자로 하는 경우에도 이중 따옴표로 묶습니다. XMLElement에 대한 두 번째 인수는 현재 생성하고 있는 요소에 값을 제공하는 열 이름입니다.
이번 데이타 전달에는 관광 명소 이름 뿐만 아니라 다른 정보도 전달하려 합니다. 목록 1과 같이 XMLElement에 호출을 중첩하여 각각의 관광 명소에 하위 요소를 생성할 수 있습니다. XMLElement에 대한 외부 호출은 <Attraction> 요소를 생성합니다. XMLElement에 대한 내부 호출은 중첩된 <Name>, <Location>, <URL> 요소를 생성합니다. XMLAttributes를 외부 XMLElement 함수 호출의 둘째 인수로 사용하는 것에 유의하십시오. XMLAttributes의 호출은 XMLElements에 선택적으로 쓸 수 있는 둘째 인수이며 이 경우에는 각 <Attraction> 태그에서 볼 수 있는 GOV 특성이 만들어집니다.
XMLElement 함수가 문자열 값이 아니라 XMLType 값을 반환한다는 점을 이해하는 것이 중요합니다. 목록에 문자가 표시되는 것은 SQL*Plus(Oracle9i Release 2)가 여러분이 선택한 모든 XMLType 값에 대해 XML 텍스트를 암묵적으로 추출하여 표시하기 때문입니다. SQL*Plus를 사용하여 이 문서에서 그 예제를 재현해 보려면, 여기에서 테이블 생성 스크립트를 다운로드하십시오. SQL*Plus에서는 XML 출력이 절단되지 않도록 SET LONG 2000 명령을 내리고, 선택적으로 SET PAGESIZE 80 명령을 내려 XML 출력에 성가신 페이지 구분이 생기지 않도록 합니다.
Null 요소의 처리
관계형 데이타를 다룰 때는 null 값이 나타날 가능성을 반드시 고려해야 합니다. 예를 들어 LOCATION 열이 일부 관광 명소에 대해 null인 경우에는 어떨까요? XMLElement을 사용하는 경우 null 열 값은 목록 2의 첫번째 질의와 결과에 나타난 바와 같이 빈 요소로 나타납니다. XML에 이러한 빈 요소를 두고 싶지 않다면 최소한 두 가지 해결책이 있습니다.
빈 XML 요소 생성을 방지하는 데 사용할 수 있는 방법 중 하나는 SQL CASE 표현식을 사용하여 열의 null 값을 테스트하고 null 또는 XMLElement의 결과를 반환하는 것입니다. 목록 2의 둘째 질의가 이 방법을 구현한 것입니다. 문제의 열이 null인 경우 각 CASE 표현식 결과는 항상 null이며, 내부 XMLElement 함수에 null이 아닌 값을 전달합니다. 외부 XMLElement은 null이 아닌 모든 값을 끌어모으며 빈 XML 요소가 될 모든 null은 무시됩니다.
빈 XML 요소 생성을 방지하는 또 다른 방법은 XMLForest 함수를 사용하는 것입니다. XML에서는 <Attraction> 아래 중첩된 요소들을 "포리스트(forest)"라 부릅니다. XMLForest를 이용하면 단 하나의 함수 호출을 가진 요소의 포리스트(forest)를 생성할 수 있습니다. 이러한 요소를 생성할 때 XMLForest는 null 값을 가진 요소들은 생략합니다. 이러한 결과를 다음 질의의 출력에서 볼 수 있습니다. 여기서 XMLForest는 질의 결과에서 null <location> 요소를 산출하지 않습니다.
SELECT XMLElement("Attraction",
XMLAttributes(government_owned AS GOV),
XMLForest(attraction_name AS "Name",
Location AS "Location",
attraction_url AS "URL"))
FROM attraction
WHERE attraction_name=`Mackinac Bridge`;
XMLELEMENT("ATTRACTION",XMLATTRIBUTES(GOV
-------------------------------------------------
<Attraction GOV="Y">
<Name>Mackinac Bridge</Name>
<URL>http://www.mackinacbridge.org/</URL>
</Attraction>
이 질의는 XMLForest에 한 번 호출하므로 목록 2에서와 같이 XMLElement에 세 번 호출하는 경우보다 입력하기 쉽고 입력 오류의 여지도 적습니다. 두 경우 모두, 질의 결과에서 null 요소가 제거됩니다. XMLForest 사용의 단점은 요소 특성을 지정할 수 없다는 점입니다. 요소에 특성을 지정해야 한다면 반드시 XMLElement를 XMLAttributes와 함께 사용해야 합니다.
XML 요소의 집계
앞의 질의는 각 관광 명소마다 별도의 XML 문서를 생성했습니다. 이는 그다지 현실적인 시나리오는 아닙니다. 관광 명소에 대한 데이타를 비즈니스 파트너에게 제공하는 경우에는 어떤 식으로든 데이타를 집계하고자 할 것입니다. 예를 들어 한 나라의 모든 관광 명소를 한 데 모아 한 문서로 전송하고자 할 수도 있습니다. 이 경우에는 XMLAgg 함수를 GROUP BY 질의와 함께 사용하면 그렇게 할 수 있습니다.
XMLAgg는 MIN, MAX, AVG 등과 같은 집계 함수입니다. 이 함수 사용의 핵심은 어떤 같은 값에 따라 데이타를 그룹으로 묶는 것입니다. 목록 3에서 질의는 데이타를 나라 이름으로 묶습니다. 그러면 XMLAgg 함수는 해당 나라의 모든 개별 <Attraction> 요소들을 가져와 한 데 연결하여 단일한 XMLType 값으로 반환하고, 그 값은 <County> 요소를 생성하는 새로운 포함 XMLElement 함수 호출로 입력됩니다. 그 결과는 목록 3< county. per document XML one returns> 에서 확인 하실 수 있습니다. 목록 3에서 XMLAttributes이 여러 특성 값을 생성하는 데 사용되는 것을 보게 됩니다.
XMLAttributes에 대한 가장 바깥 쪽의 호출은 세 개의 특성 즉, 나라 이름에 대한 것 하나, 그리고 해당 문서가 따르는 XML 스키마를 가리키는 것 둘을 생성합니다. 여기서 질의는 GROUP BY이므로 가장 바깥 쪽의 XMLElement 함수 호출과 그와 연관된 XMLAttributes 호출은 요약된 열만을 참조할 수 있습니다. c.county_name 대신 a.county_name을 사용하면 오류가 나타나는데 이는 a.county_name이 GROUP BY 표현식이 아니기 때문입니다.
기타 아래의 내용도 한번 참고 해 보세요...
SQL/XML 표준 학습
http://www.sqlx.org
Oracle SQL/XML에 대한 상세 정보
http://www.oracle.com/otn.oracle.com/tech/xml/
http://www.oracle.com/xmldb/htdocs/sql_xml.html
이 문서의 테이블 생성 코드 다운로드
http://www.oracle.com/otn.oracle.com/oramag/oracle/03-may/o33xml_tablecreate.zip
XML DB 데모
http://www.oracle.com/otn.oracle.com/tech/xml/xmldb
관련 자료 읽기
http://www.oracle.com//kr/magazine/webcolumns/2003/o13xml.html
XML DB에 대하여
http://otn.oracle.co.kr/tech/xml
technet.oracle.co.kr에 있는 내용 입니다.
참고 하세요~
'DB' 카테고리의 다른 글
[QUERY] 중복데이터 제거 (0) | 2006.07.21 |
---|---|
[대용량데이터베이스] 조인의 최적화 (0) | 2006.07.20 |
[QUERY] COUNT(*)를 빠르게 (0) | 2006.07.16 |
[QUERY] index rebuild 예 (0) | 2006.07.16 |
[QUERY] 실행중인(ACTIVE) SQL문 확인 (0) | 2006.07.16 |