2009-10-05 28 views
7

Cách tốt nhất để đi về việc băm một tài liệu XML trong C# là gì? Tôi muốn băm một tài liệu XML để tôi có thể biết nếu nó được thay đổi theo cách thủ công từ khi nó được tạo ra. Tôi không sử dụng điều này để bảo mật - OK nếu ai đó thay đổi XML và thay đổi giá trị băm để phù hợp.Tạo một băm tài liệu XML trong C#

Ví dụ, tôi muốn băm các nút con của thư mục gốc và lưu trữ các hash như một thuộc tính của thư mục gốc:

<RootNode Hash="abc123"> 
    <!-- Content to hash here --> 
</RootNode> 
+0

Khoảng trắng được phát trong băm mong muốn của bạn như thế nào? –

+0

Tôi đang ở hàng rào về điều đó - một mặt, tôi chỉ thực sự quan tâm đến dữ liệu chứ không phải định dạng. Mặt khác, việc xác định * mọi thay đổi * có thể hữu ích để kiểm tra xem có ai đó đang chơi với tệp không. –

Trả lời

7

.NET có classes triển khai XML digital signature spec. Chữ ký có thể được thêm vào bên trong tài liệu XML gốc (tức là "chữ ký bao bọc") hoặc được lưu trữ/chuyển riêng.

Có thể hơi quá mức vì bạn không cần bảo mật, nhưng nó có lợi thế là đã được triển khai và là tiêu chuẩn không phụ thuộc vào ngôn ngữ hoặc nền tảng.

+0

Tôi thích giải pháp này, bởi vì như bạn đã chỉ ra, nó đã được thực hiện và là một tiêu chuẩn. –

4

Bạn có thể sử dụng không gian tên mật mã:

System.Security.Cryptography.MACTripleDES hash = new System.Security.Cryptography.MACTripleDES(Encoding.Default.GetBytes("mykey")); 
string hashString = Convert.ToBase64String(hash.ComputeHash(Encoding.Default.GetBytes(myXMLString))); 

Bạn chỉ cần sử dụng một chìa khóa để tạo ra mật mã băm và sau đó tạo ra một băm với chuỗi reqpresentation của xml của bạn.

+1

xem thêm System.Security.Cryptography.MD5, System.Security.Cryptography.SHA1, System.Security.Cryptography.SHA256, v.v. và xem lại so sánh ở đây: http://en.wikipedia.org/wiki/Cryptographic_hash_function –

+2

Mã hóa. Mặc định là mã hóa cho trang mã ANSI hiện tại của hệ điều hành. Do đó, mã của bạn sẽ cung cấp các kết quả khác nhau tùy thuộc vào các cài đặt trong Tùy chọn ngôn ngữ và khu vực - tab Nâng cao. –

+0

wcoenen có một điểm rất công bằng. Sử dụng Encoding.ASCII hoặc Encoding. . –

2

Thêm tham chiếu .NET vào System.Security và sử dụng XmlDsigC14NTransform. Dưới đây là ví dụ ...

/* http://www.w3.org/TR/xml-c14n 

    Of course is cannot detect these are the same... 

     <color>black</color> vs. <color>rgb(0,0,0)</color> 

    ...because that's dependent on app logic's interpretation of XML data. 

    But otherwise it gets the following right... 
    •Normalization of whitespace in start and end tags 
    •Lexicographic ordering of namespace and attribute 
    •Empty element conversion to start-end tag pair 
    •Retain all whitespace between tags 

    And more. 
*/ 
public static string XmlHash(XmlDocument myDoc) 
{ 
    var t = new System.Security.Cryptography.Xml.XmlDsigC14NTransform(); 
    t.LoadInput(myDoc); 
    var s = (Stream)t.GetOutput(typeof(Stream)); 
    var sha1 = SHA1.Create(); 

    var hash = sha1.ComputeHash(s); 
    var base64String = Convert.ToBase64String(hash); 
    s.Close(); 
    return base64String; 
} 
Các vấn đề liên quan