2017-05-05 67 views
0

我有以下类型的结果集的甲骨文从数据库返回的:执行子查询的一个结果在Oracle中创建一个XML

**Name Type SubName  Number** 
test B  tim   1 
test B  jfd   2 
testV I  rr    1 
testV I  sim   2 
dsgsg B  sgsg   1 
dsgsg B  sfsfssfsffs 2 

我想是使用SQL创建一个操纵这个结果这种类型的

<NameList> 
<Name/> 
<Type/> 
<SubNameList> 
<SubName> 
<Name/> 
<Number/> 
</SubName> 
</SubNameList> 
</NameList> 

例如XML:对于前两条记录结果集的名称相同,因此XML将是:

<NameList> 
<Name>test</Name> 
<Type>B</Type> 
<SubNameList> 
<SubName> 
<Name>tim</Name> 
<Number>1</Number> 
</SubName> 
<SubName> 
<Name>jfd</Name> 
<Number>2</Number> 
</SubName> 
</SubNameList> 
</NameList> 

我迄今所做的: 我有两个表为:

TABLE1 
    **ID NAME KEY** 
     1 test 101 
     1 testV 102 
     1 dsgsg 103 

TABLE2 
    **ID SUBNAME TYPE NUMBER KEY** 
     1 tim  B 1  101 
     1 jfd  B 2  101 
     1 rr  I 1  102 
     1 sim  I 2  102 
     1 sgsg B 1  103 
     1 sfsfssfsffs B 2  103 

SQL:

Select A.NAME, B.TYPE, B.SUBNAME, B.NUMBER 
FROM TABLE1 A INNER JOIN TABLE2 B 
ON A.ID = B.ID WHERE A.ID = '1'; 

我一直在使用XMLELEMENT()创建的XML在Oracle为:

SET SERVEROUTPUT ON; 
DECLARE NAME_XML XMLTYPE; 
v_offset number := 1; 
v_chunk_size number := 255; 
BEGIN 
Select XMLAGG(XMLELEMENT("NAMELIST", 
XMLELEMENT("Name", A.NAME), 
XMLELEMENT("Type", B.TYPE), 
XMLELEMENT("SubName", B.SUBNAME), 
XMLELEMENT("Number", B.NUMBER))) 
INTO NAME_XML 
FROM TABLE1 A INNER JOIN TABLE2 B 
ON A.ID = B.ID WHERE A.ID = '1'; 

loop 
    exit when v_offset > dbms_lob.getlength(NAME_XML.getClobVal()); 
    dbms_output.put_line(dbms_lob.substr(NAME_XML.getClobVal(), 
    v_chunk_size, v_offset)); 
    v_offset := v_offset + v_chunk_size; 
end loop; 
END; 

该XML正在建造中:

<?xml version="1.0" encoding="UTF-8"?> 
<root> 
    <NAMELIST> 
     <Name>test</Name> 
     <Type>B</Type> 
     <SubName>tim</SubName> 
     <Number>1</Number> 
    </NAMELIST> 
. 
. 
. 
. 
. 
    <NAMELIST> 
     <Name>dsgsg</Name> 
     <Type>B</Type> 
     <SubName>sfsfssfsffs</SubName> 
     <Number>2</Number> 
    </NAMELIST> 
</root> 

我怎样才能实现这种类型的XML格式:

<NameList> 
<Name>test</Name> 
<Type>B</Type> 
<SubNameList> 
<SubName> 
<Name>tim</Name> 
<Number>1</Number> 
</SubName> 
<SubName> 
<Name>jfd</Name>    
<Number>2</Number> 
</SubName> 
</SubNameList> 
</NameList> 
.... 
.... 
.... 
.... 

任何投入将是有益的。

+0

@jarlh我使用Oracle并从中删除了mysql标签 –

回答

0

我没有你的表格,所以我从双选择一些固定值。没有漂亮的打印输出。

declare 
    name_xml  xmltype; 
    v_offset  number := 1; 
    v_chunk_size number := 255; 
begin 
    select xmlagg(xmlelement("NAMELIST" 
          ,xmlelement("Name", 'Peter') 
          ,xmlelement("Type", 'mytype') 
          ,xmlelement("SubName", 'SUBNAME', xmlelement("Number", 'B.NUMBER')))) 
    into name_xml 
    from dual; 

    loop 
     exit when v_offset > dbms_lob.getlength(name_xml.getclobval()); 
     dbms_output.put_line(dbms_lob.substr(name_xml.getclobval(), v_chunk_size, v_offset)); 
     v_offset := v_offset + v_chunk_size; 
    end loop; 
end; 


<NAMELIST><Name>Peter</Name><Type>mytype</Type><SubName>SUBNAME<Number>B.NUMBER</Number></SubName></NAMELIST> 
0

您可以使用程序,因为这一个:

CREATE OR REPLACE PROCEDURE MakePrettyXml(xmlString IN OUT NOCOPY CLOB, intent IN VARCHAR2 DEFAULT 'yes') IS 

    xmlDocFragment DBMS_XMLDOM.DOMDOCUMENTFRAGMENT; 
    xslProc DBMS_XSLPROCESSOR.PROCESSOR; 
    xsl DBMS_XSLPROCESSOR.STYLESHEET; 
    xmlStringOut CLOB; 

BEGIN 

    DBMS_LOB.CREATETEMPORARY(xmlStringOut, TRUE); 
    xslProc := DBMS_XSLPROCESSOR.NEWPROCESSOR; 
    xsl := DBMS_XSLPROCESSOR.NEWSTYLESHEET(
     '<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">'|| 
      '<xsl:output method="xml" indent="'||intent||'"/>'|| 
      '<xsl:template match="@*|node()">'|| 
       '<xsl:copy>'|| 
        '<xsl:apply-templates select="@*|node()"/>'|| 
       '</xsl:copy>'|| 
      '</xsl:template>'|| 
     '</xsl:stylesheet>', NULL); 

    xmlDocFragment := DBMS_XSLPROCESSOR.PROCESSXSL(p => xslProc, ss => xsl, cl => xmlString); 
    DBMS_XMLDOM.WRITETOCLOB(DBMS_XMLDOM.MAKENODE(xmlDocFragment), xmlStringOut); 

    DBMS_XSLPROCESSOR.FREESTYLESHEET(xsl); 
    DBMS_XSLPROCESSOR.FREEPROCESSOR(xslProc); 

    xmlString := xmlStringOut; 
    DBMS_LOB.FREETEMPORARY(xmlStringOut); 

END MakePrettyXml; 

结果:

DECLARE 
    xmlString CLOB := '<root><NAMELIST> 
     <Name>test</Name><Type>B</Type><SubName>tim</SubName><Number>1</Number> 
    </NAMELIST> 
    <NAMELIST> 
     <Name>dsgsg</Name> 
     <Type>B</Type><SubName>sfsfssfsffs</SubName> 
     <Number>2</Number> 
    </NAMELIST> 
</root>'; 

BEGIN 

    MakePrettyXml(xmlString, 'no'); 
    DBMS_OUTPUT.PUT_LINE(xmlString); 

    MakePrettyXml(xmlString); 
    DBMS_OUTPUT.PUT_LINE(xmlString); 

END; 

<root> 
<NAMELIST> 
<Name>test</Name> 
<Type>B</Type> 
<SubName>tim</SubName> 
<Number>1</Number> 
</NAMELIST> 
<NAMELIST> 
<Name>dsgsg</Name> 
<Type>B</Type> 
<SubName>sfsfssfsffs</SubName> 
<Number>2</Number> 
</NAMELIST> 
</root> 

<root> 
    <NAMELIST> 
    <Name>test</Name> 
    <Type>B</Type> 
    <SubName>tim</SubName> 
    <Number>1</Number> 
    </NAMELIST> 
    <NAMELIST> 
    <Name>dsgsg</Name> 
    <Type>B</Type> 
    <SubName>sfsfssfsffs</SubName> 
    <Number>2</Number> 
    </NAMELIST> 
</root> 

更新

我希望你的问题是有关XML的内容,而不是格式。在这种情况下可以尝试(未测试)

Select XMLELEMENT("NameList", 
    XMLELEMENT("Name", A.NAME), 
    XMLELEMENT("Type", B.TYPE), 
    XMLELEMENT("SubNameList", 
    XMLAGG(XMLELEMENT("SubName", 
    XMLELEMENT("Name", B.NAME) 
    XMLELEMENT("Number", B.NUMBER)))) 
    ) 
INTO NAME_XML 
FROM TABLE1 A INNER JOIN TABLE2 B 
ON A.ID = B.ID WHERE A.ID = '1'; 
0

我能得到这个..

SQL> set pages 0 
SQL> WITH TABLE1 AS 
    2 (
    3 SELECT 1 AS ID, 'test' as NAME, 101 as KEY 
    4 from DUAL 
    5 UNION ALL 
    6 SELECT 1 AS ID, 'testV' as NAME, 102 as KEY 
    7 from DUAL 
    8 UNION ALL 
    9 SELECT 1 AS ID, 'dsgsg' as NAME, 103 as KEY 
10 from DUAL 
11 ), 
12 TABLE2 as 
13 (
14 SELECT 1 AS ID, 'tim' as SUBNAME, 'B' as TYPE, 1 as "NUMBER",101 as KEY 
15 from DUAL 
16 UNION ALL 
17 SELECT 1 AS ID, 'jfd' as SUBNAME, 'B' as TYPE, 2 as "NUMBER",101 as KEY 
18 from DUAL 
19 UNION ALL 
20 SELECT 1 AS ID, 'rr' as SUBNAME, 'I' as TYPE, 1 as "NUMBER",102 as KEY 
21 from DUAL 
22 UNION ALL 
23 SELECT 1 AS ID, 'sim' as SUBNAME, 'I' as TYPE, 2 as "NUMBER",102 as KEY 
24 from DUAL 
25 UNION ALL 
26 SELECT 1 AS ID, 'sgsg' as SUBNAME, 'B' as TYPE, 1 as "NUMBER",103 as KEY 
27 from DUAL 
28 UNION ALL 
29 SELECT 1 AS ID, 'sfsfssfsffs' as SUBNAME, 'B' as TYPE, 2 as "NUMBER", 103 as KEY 
30 from DUAL 
31 ) 
32 select XMLSERIALIZE(DOCUMENT 
33   xmlElement("NameList", 
34    xmlElement("Name", NAME), 
35  xmlElement(
36    "SubNameList",(
37     select xmlAgg(
38       xmlElement(
39       "SubName", 
40        XMLELEMENT("Name", SUBNAME), 
41        XMLELEMENT("Number", "NUMBER"), 
42        XMLELEMENT("Type", TYPE) 
43       ) 
44      ) 
45     from TABLE2 T2 
46     where T2.ID = T1.ID 
47   )) 
48   ) 
49   AS VARCHAR2(4000) INDENT SIZE=2 
50  ) 
51 from TABLE1 T1 
52 WHERE T1.ID = '1' 
53/
<NameList> 
    <Name>test</Name> 
    <SubNameList> 
    <SubName> 
     <Name>tim</Name> 
     <Number>1</Number> 
     <Type>B</Type> 
    </SubName> 
    <SubName> 
     <Name>jfd</Name> 
     <Number>2</Number> 
     <Type>B</Type> 
    </SubName> 
    <SubName> 
     <Name>rr</Name> 
     <Number>1</Number> 
     <Type>I</Type> 
    </SubName> 
    <SubName> 
     <Name>sim</Name> 
     <Number>2</Number> 
     <Type>I</Type> 
    </SubName> 
    <SubName> 
     <Name>sgsg</Name> 
     <Number>1</Number> 
     <Type>B</Type> 
    </SubName> 
    <SubName> 
     <Name>sfsfssfsffs</Name> 
     <Number>2</Number> 
     <Type>B</Type> 
    </SubName> 
    </SubNameList> 
</NameList> 

<NameList> 
    <Name>testV</Name> 
    <SubNameList> 
    <SubName> 
     <Name>tim</Name> 
     <Number>1</Number> 
     <Type>B</Type> 
    </SubName> 
    <SubName> 
     <Name>jfd</Name> 
     <Number>2</Number> 
     <Type>B</Type> 
    </SubName> 
    <SubName> 
     <Name>rr</Name> 
     <Number>1</Number> 
     <Type>I</Type> 
    </SubName> 
    <SubName> 
     <Name>sim</Name> 
     <Number>2</Number> 
     <Type>I</Type> 
    </SubName> 
    <SubName> 
     <Name>sgsg</Name> 
     <Number>1</Number> 
     <Type>B</Type> 
    </SubName> 
    <SubName> 
     <Name>sfsfssfsffs</Name> 
     <Number>2</Number> 
     <Type>B</Type> 
    </SubName> 
    </SubNameList> 
</NameList> 

<NameList> 
    <Name>dsgsg</Name> 
    <SubNameList> 
    <SubName> 
     <Name>tim</Name> 
     <Number>1</Number> 
     <Type>B</Type> 
    </SubName> 
    <SubName> 
     <Name>jfd</Name> 
     <Number>2</Number> 
     <Type>B</Type> 
    </SubName> 
    <SubName> 
     <Name>rr</Name> 
     <Number>1</Number> 
     <Type>I</Type> 
    </SubName> 
    <SubName> 
     <Name>sim</Name> 
     <Number>2</Number> 
     <Type>I</Type> 
    </SubName> 
    <SubName> 
     <Name>sgsg</Name> 
     <Number>1</Number> 
     <Type>B</Type> 
    </SubName> 
    <SubName> 
     <Name>sfsfssfsffs</Name> 
     <Number>2</Number> 
     <Type>B</Type> 
    </SubName> 
    </SubNameList> 
</NameList> 


SQL> 
SQL> 

但我不知道如何TYPE是为了图成所需要的结果..

相关问题