xml.dom.minidom --- Triển khai DOM tối thiểu¶
Source code: Lib/xml/dom/minidom.py
xml.dom.minidom là một triển khai tối thiểu của giao diện Mô hình đối tượng tài liệu, với API tương tự như trong các ngôn ngữ khác. Nó được thiết kế đơn giản hơn DOM đầy đủ và cũng nhỏ hơn đáng kể. Thay vào đó, những người dùng chưa thành thạo với DOM nên cân nhắc sử dụng mô-đun xml.etree.ElementTree để xử lý XML.
Ghi chú
Nếu bạn cần phân tích dữ liệu không đáng tin cậy hoặc chưa được xác thực, hãy xem bảo mật XML.
Các ứng dụng DOM thường bắt đầu bằng cách phân tích một số XML thành DOM. Với xml.dom.minidom, việc này được thực hiện thông qua các hàm phân tích cú pháp:
từ phân tích cú pháp nhập xml.dom.minidom, ParseString
dom1 = parse('c:\\temp\\mydata.xml') # parse một tệp XML theo tên
nguồn dữ liệu = open('c:\\temp\\mydata.xml')
dom2 = phân tích cú pháp (nguồn dữ liệu) # parse một tệp đang mở
dom3 = ParseString('<myxml>Một số dữ liệu<empty/> một số dữ liệu khác</myxml>')
Hàm parse() có thể lấy tên tệp hoặc đối tượng tệp đang mở.
- xml.dom.minidom.parse(filename_or_file, parser=None, bufsize=None)¶
Trả về
Documenttừ đầu vào đã cho. filename_or_file có thể là tên tệp hoặc đối tượng giống như tệp. parser, nếu được cung cấp, phải là đối tượng phân tích cú pháp SAX2. Hàm này sẽ thay đổi trình xử lý tài liệu của trình phân tích cú pháp và kích hoạt hỗ trợ không gian tên; cấu hình trình phân tích cú pháp khác (như đặt trình phân giải thực thể) phải được thực hiện trước.
Nếu bạn có XML trong một chuỗi, bạn có thể sử dụng hàm parseString() thay thế:
- xml.dom.minidom.parseString(string, parser=None)¶
Trả về
Documentđại diện cho string. Phương thức này tạo một đối tượngio.StringIOcho chuỗi và chuyển nó sangparse().
Cả hai hàm đều trả về một đối tượng Document đại diện cho nội dung của tài liệu.
Chức năng của parse() và parseString() là kết nối trình phân tích cú pháp XML với "trình tạo DOM" có thể chấp nhận các sự kiện phân tích cú pháp từ bất kỳ trình phân tích cú pháp SAX nào và chuyển đổi chúng thành cây DOM. Tên của các chức năng có thể gây nhầm lẫn nhưng lại dễ nắm bắt khi tìm hiểu các giao diện. Việc phân tích tài liệu sẽ được hoàn thành trước khi các hàm này quay trở lại; đơn giản là các hàm này không cung cấp khả năng triển khai trình phân tích cú pháp.
Bạn cũng có thể tạo Document bằng cách gọi một phương thức trên đối tượng "Triển khai DOM". Bạn có thể lấy đối tượng này bằng cách gọi hàm getDOMImplementation() trong gói xml.dom hoặc mô-đun xml.dom.minidom. Sau khi có Document, bạn có thể thêm các nút con vào đó để điền vào DOM:
từ xml.dom.minidom nhập getDOMImplementation
impl = getDOMImplementation()
newdoc = impl.createDocument(Không có, "some_tag", Không có)
top_element = newdoc.documentElement
text = newdoc.createTextNode('Một số nội dung văn bản.')
top_element.appendChild(văn bản)
Khi bạn có đối tượng tài liệu DOM, bạn có thể truy cập các phần của tài liệu XML thông qua các thuộc tính và phương thức của nó. Các thuộc tính này được xác định trong đặc tả DOM. Thuộc tính chính của đối tượng tài liệu là thuộc tính documentElement. Nó cung cấp cho bạn thành phần chính trong tài liệu XML: thành phần chứa tất cả những thành phần khác. Đây là một chương trình ví dụ:
dom3 = ParseString("<myxml>Một số dữ liệu</myxml>")
khẳng định dom3.documentElement.tagName == "myxml"
Khi bạn hoàn thành với cây DOM, bạn có thể tùy ý gọi phương thức unlink() để khuyến khích việc dọn dẹp sớm các đối tượng hiện không cần thiết. unlink() là một phần mở rộng dành riêng cho xml.dom.minidom- của DOM API khiến nút và các nút con của nó về cơ bản trở nên vô dụng. Nếu không, trình thu gom rác của Python cuối cùng sẽ xử lý các đối tượng trong cây.
Xem thêm
- Document Object Model (DOM) Level 1 Specification
Đề xuất W3C cho DOM được
xml.dom.minidomhỗ trợ.
Đối tượng DOM¶
Định nghĩa về DOM API cho Python được đưa ra như một phần của tài liệu mô-đun xml.dom. Phần này liệt kê những khác biệt giữa API và xml.dom.minidom.
- Node.unlink()¶
Phá vỡ các tham chiếu nội bộ trong DOM để nó sẽ được thu thập rác trên các phiên bản Python không có GC tuần hoàn. Ngay cả khi có sẵn GC tuần hoàn, việc sử dụng tính năng này có thể cung cấp lượng lớn bộ nhớ sớm hơn, do đó, việc gọi tính năng này trên các đối tượng DOM ngay khi chúng không còn cần thiết là một cách làm tốt. Điều này chỉ cần được gọi trên đối tượng
Document, nhưng có thể được gọi trên các nút con để loại bỏ các nút con của nút đó.Bạn có thể tránh gọi phương thức này một cách rõ ràng bằng cách sử dụng câu lệnh
with. Đoạn mã sau sẽ tự động hủy liên kết dom khi thoát khốiwithvới xml.dom.minidom.parse(datasource) là dom: ... # Work với dom.
- Node.writexml(writer, indent='', addindent='', newl='', encoding=None, standalone=None)¶
Viết XML cho đối tượng nhà văn. Người viết nhận được văn bản nhưng không phải byte làm đầu vào, nó phải có phương thức
write()khớp với phương thức của giao diện đối tượng tệp. Tham số indent là thụt lề của nút hiện tại. Tham số addindent là mức thụt lề tăng dần để sử dụng cho các nút con của nút hiện tại. Tham số newl chỉ định chuỗi sử dụng để chấm dứt dòng mới.Đối với nút
Document, một đối số từ khóa bổ sung encoding có thể được sử dụng để chỉ định trường mã hóa của tiêu đề XML.Tương tự, việc nêu rõ đối số standalone sẽ khiến các khai báo tài liệu độc lập được thêm vào phần mở đầu của tài liệu XML. Nếu giá trị được đặt thành
True,standalone="yes"sẽ được thêm vào, nếu không thì giá trị được đặt thành"no". Không nêu đối số sẽ bỏ qua phần khai báo khỏi tài liệu.Thay đổi trong phiên bản 3.8: Phương thức
writexml()hiện giữ nguyên thứ tự thuộc tính do người dùng chỉ định.Thay đổi trong phiên bản 3.9: Tham số standalone đã được thêm vào.
- Node.toxml(encoding=None, standalone=None)¶
Trả về một chuỗi hoặc chuỗi byte chứa XML được đại diện bởi nút DOM.
Với đối số encoding [1] rõ ràng, kết quả là một chuỗi byte trong mã hóa được chỉ định. Không có đối số encoding, kết quả là một chuỗi Unicode và khai báo XML trong chuỗi kết quả không chỉ định mã hóa. Mã hóa chuỗi này bằng mã hóa khác UTF-8 có thể không chính xác vì UTF-8 là mã hóa mặc định của XML.
Đối số standalone hoạt động chính xác như trong
writexml().Thay đổi trong phiên bản 3.8: Phương thức
toxml()hiện giữ nguyên thứ tự thuộc tính do người dùng chỉ định.Thay đổi trong phiên bản 3.9: Tham số standalone đã được thêm vào.
- Node.toprettyxml(indent='\t', newl='\n', encoding=None, standalone=None)¶
Trả lại một phiên bản tài liệu được in đẹp. indent chỉ định chuỗi thụt lề và mặc định là trình lập bảng; newl chỉ định chuỗi phát ra ở cuối mỗi dòng và mặc định là
\n.Đối số encoding hoạt động giống như đối số tương ứng của
toxml().Đối số standalone hoạt động chính xác như trong
writexml().Thay đổi trong phiên bản 3.8: Phương thức
toprettyxml()hiện giữ nguyên thứ tự thuộc tính do người dùng chỉ định.Thay đổi trong phiên bản 3.9: Tham số standalone đã được thêm vào.
DOM Ví dụ¶
Chương trình ví dụ này là một ví dụ khá thực tế về một chương trình đơn giản. Trong trường hợp cụ thể này, chúng tôi không tận dụng được nhiều lợi thế về tính linh hoạt của DOM.
nhập xml.dom.minidom
tài liệu = """\
<trình chiếu>
<title>Trình chiếu demo</title>
<slide><title>Tiêu đề trang trình bày</title>
<point>Đây là bản demo</point>
<point>Của chương trình xử lý slide</point>
</slide>
<slide><title>Một slide demo khác</title>
<point>Điều quan trọng</point>
<point>Để có nhiều hơn</point>
<point>một slide</point>
</slide>
</trình chiếu>
"""
dom = xml.dom.minidom.parseString(tài liệu)
def getText(danh sách nút):
rc = []
cho nút trong danh sách nút:
nếu node.nodeType == node.TEXT_NODE:
RC.append(node.data)
return ''.join(rc)
def xử lýSlideshow(trình chiếu):
in("<html>")
handSlideshowTitle(slideshow.getElementsByTagName("title")[0])
slide = slideshow.getElementsByTagName("slide")
xử lýToc(slide)
xử lýSlide(slide)
in("</html>")
def xử lýSlides(slide):
cho slide trong slide:
xử lýSlide(trượt)
def xử lýSlide(trượt):
handSlideTitle(slide.getElementsByTagName("title")[0])
handPoints(slide.getElementsByTagName("point"))
def xử lýSlideshowTitle(title):
print(f"<title>{getText(title.childNodes)</title>")
def xử lýSlideTitle(title):
print(f"<h2>{getText(title.childNodes)</h2>")
def xử lýPoints(điểm):
in("<ul>")
cho điểm trong điểm:
xử lýPoint(điểm)
in("</ul>")
def xử lýPoint(điểm):
print(f"<li>{getText(point.childNodes)</li>")
def handToc(slide):
cho slide trong slide:
tiêu đề = slide.getElementsByTagName("title")[0]
print(f"<p>{getText(title.childNodes)</p>")
xử lýSlideshow(dom)
minidom và tiêu chuẩn DOM¶
Mô-đun xml.dom.minidom về cơ bản là DOM tương thích với DOM 1.0 với một số tính năng của DOM 2 (chủ yếu là các tính năng không gian tên).
Việc sử dụng giao diện DOM trong Python rất đơn giản. Các quy tắc ánh xạ sau đây được áp dụng:
Các giao diện được truy cập thông qua các đối tượng thể hiện. Các ứng dụng không nên tự khởi tạo các lớp; họ nên sử dụng các hàm tạo có sẵn trên đối tượng
Document. Giao diện phái sinh hỗ trợ tất cả các hoạt động (và thuộc tính) từ giao diện cơ sở, cộng với mọi hoạt động mới.Hoạt động được sử dụng như phương pháp. Vì DOM chỉ sử dụng tham số
innên các đối số được truyền theo thứ tự bình thường (từ trái sang phải). Không có đối số tùy chọn. Hoạt độngvoidtrả vềNone.Thuộc tính IDL ánh xạ tới các thuộc tính thể hiện. Để tương thích với ánh xạ ngôn ngữ OMG IDL cho Python, thuộc tính
foocũng có thể được truy cập thông qua các phương thức truy cập_get_foo()và_set_foo(). Thuộc tínhreadonlykhông được thay đổi; điều này không được thực thi trong thời gian chạy.Các loại
short int,unsigned int,unsigned long longvàbooleanđều ánh xạ tới các đối tượng số nguyên Python.Loại
DOMStringánh xạ tới chuỗi Python.xml.dom.minidomhỗ trợ byte hoặc chuỗi nhưng thường sẽ tạo ra chuỗi. Các giá trị của loạiDOMStringcũng có thể làNonekhi được phép có giá trị IDLnulltheo thông số DOM từ W3C.Khai báo
constánh xạ tới các biến trong phạm vi tương ứng của chúng (ví dụ:xml.dom.minidom.Node.PROCESSING_INSTRUCTION_NODE); chúng không được thay đổi.DOMExceptionhiện không được hỗ trợ trongxml.dom.minidom. Thay vào đó,xml.dom.minidomsử dụng các ngoại lệ Python tiêu chuẩn nhưTypeErrorvàAttributeError.Các đối tượng
NodeListđược triển khai bằng loại danh sách có sẵn của Python. Các đối tượng này cung cấp giao diện được xác định trong đặc tả DOM, nhưng với các phiên bản Python trước đó, chúng không hỗ trợ API chính thức. Tuy nhiên, chúng "Pythonic" hơn nhiều so với giao diện được xác định trong khuyến nghị W3C.
Các giao diện sau không được triển khai trong xml.dom.minidom:
DOMTimeStampEntityReference
Hầu hết những thông tin này phản ánh thông tin trong tài liệu XML không có ích chung cho hầu hết người dùng DOM.
Chú thích cuối trang