2010-01-07 16 views
6

Tôi biết đây là một trường hợp biên giới cho dù nó thực sự thuộc về stackoverflow hay superuser, nhưng có vẻ như có khá ít 'chỉnh sửa mã' câu hỏi ở đây, tôi đăng nó lên SO.Làm thế nào để có được một XML phẳng để các thực thể bên ngoài được hợp nhất với cấp cao nhất

Tôi có một đống tệp XML mà một người nào đó trong trí tuệ vô hạn của họ đã quyết định phát nổ tới nhiều tệp bằng cách sử dụng các thẻ, điều này khiến cho việc sửa/chỉnh sửa chúng trở thành một P-i-t-A lớn. Vì vậy, tôi đang tìm kiếm:

  1. Một cách để VIM mở chúng trong một bộ đệm đơn (tốt nhất là các thay đổi được lưu trong các tệp thực thể bên ngoài chính xác), HOẶC;
  2. Cách mở rộng các tệp trong VIM sao cho các thực thể ngoài được đọc và thay thế trong bộ đệm, HOẶC;
  3. một bash dễ dàng/sed/python cách để làm điều này trên một dòng lệnh (hoặc trong vimrc)

Các tập tin bao gồm trên cấp cao nhất có thể bao gồm các file mới và như vậy trên người hiểu biết về cách nhiều cấp độ vì vậy đây cần phải được đệ quy ...

đây là một mẫu mockup vào những gì các tập tin cấp cao nhất trông giống như:

<?xml version="1.0" encoding="ISO-8859-1"?> 
<!DOCTYPE foobar PUBLIC "foobar:dtd" "foobar.dtd" [ 

     <!ENTITY foo SYSTEM "foo.xml"> 

     <!ENTITY bar SYSTEM "bar.xml"> 
]> 
<foo> 
     <params> 
       &foo; 
     </params> 
     <bar> 
       &bar; 
     </bar> 
</foo> 

EDIT: danh sách này là trong thứ tự ưu tiên - nếu không có 1. hoặc 2. Các giải pháp có sẵn, tiền thưởng đi cho tốt nhất # 3 ...

EDIT 2: Hình như @Gaby 's công trình trả lời, nhưng tiếc là chỉ có một phần, ngoại trừ tôi làm điều gì đó sai - Tôi sẽ viết một số loại công cụ sử dụng câu trả lời của anh ấy và đăng nó ở đây để cải tiến. Tất nhiên, một # 1 hoặC# 2 giải pháp sẽ được đánh giá cao ... :)

EDIT 3: Ok, tốt nhất không Emacs -answer sẽ nhận được tiền thưởng;)

Kết luận : Nhờ @hcayless bây giờ tôi có một giải pháp làm việC# 2, tôi nói thêm:

autocmd BufReadPost,FileReadPost *.xml silent %!xmllint --noent - 2> /dev/null 

để .vimrc của tôi và tất cả mọi thứ là hunky dory.

+0

Điều này có thể được thực hiện với xslt không? – michael

+1

Tôi đã không nhìn thấy điều này trước đây, nhưng rõ ràng nó là một phần trung thực cho sự tốt lành của XML. http://www.xml.com/pub/a/98/08/xmlqna2.html là một giải thích mà tôi đã tìm thấy. – MikeSep

+0

Yep, nó hợp lệ và do đó hai lần là gây phiền nhiễu :) – Kimvais

Trả lời

5

Nếu bạn đã cài đặt libxml2, thì xmllint có thể sẽ làm điều này cho bạn. Tùy thuộc vào thiết lập của bạn, bạn có thể cần thêm thông số, nhưng đối với ví dụ của bạn, nhưng ví dụ của bạn,

xmllint --noent foobar.xml 

sẽ in tệp của bạn để stdout với tất cả các thực thể được giải quyết. Nên dễ dàng, đủ để bọc một số bash scripting xung quanh nó để làm những gì bạn cần.

+0

Hoạt động hoàn hảo. Cảm ơn! - Bây giờ tôi chỉ cần thêm điều này để được thực hiện tự động trong .vimrc khi mở .xml -files. – Kimvais

1

Đối với tùy chọn # 3 bạn có thể có một cái nhìn tại pixdom và nhìn vào tài liệu tại pxdom 1.5 A Python DOM implementation

DOMConfiguration thông số

Kết quả của hoạt động phân tích cú pháp phụ thuộc vào các thông số thiết lập trên LSParser.domConfig mapping. Bởi mặc định, phù hợp với các đặc điểm kỹ thuật DOM, tất cả các phần CDATA sẽ được thay thế bằng các nút văn bản đơn giản và tất cả các tham chiếu thực thể ràng buộc sẽ thay thế bằng nội dung của các thực thể gọi. Điều này bao gồm các tham chiếu bên ngoài đối tượng và tập hợp con bên ngoài .

nó bao gồm serializer để lưu tài liệu vào một tập tin ..

0

Bạn đang tìm kiếm một cái gì đó như thế này?

#!/opt/local/bin/python 
import sys 
if len(sys.argv) < 2: 
    print "some files needed." 
    sys.exit() 

final = """ 
<?xml version="1.0" encoding="ISO-8859-1"?> 
<nodes> 
""" 
for a in sys.argv[1:]: 
    ca = a.replace(".xml","") 
    final += "<" + ca + ">\n" 
    infile = open(a) 
    final += infile.read() 
    final += "</" + ca + ">\n" 

final += "</nodes>\n" 

outfile = open("final.xml", "w") 
outfile.write(final) 
outfile.close() 
Các vấn đề liên quan