2011-12-19 43 views
7

Tôi cần trả về một đối tượng SimpleXML được chuyển đổi thành một đối tượng JSON để làm việc với nó trong JavaScript. Vấn đề là không có thuộc tính nào trên bất kỳ đối tượng nào có giá trị.Biến mất các thuộc tính trong đối tượng SimpleXML PHP?

Như một ví dụ:

<customer editable="true" maxChars="9" valueType="numeric">69236</customer> 

trở nên trong đối tượng SimpleXML:

"customer":"69236" 

đâu là đối tượng @attributes?

Trả lời

-1

Dưới đây là một số mã để lặp qua các thuộc tính và xây dựng JSON. Nếu hỗ trợ, một hoặc nhiều khách hàng.

Nếu bạn XML trông như thế này (hoặc chỉ là một khách hàng)

<xml> 
<customer editable="true" maxChars="9" valueType="numeric">69236</customer> 
<customer editable="true" maxChars="9" valueType="numeric">12345</customer> 
<customer editable="true" maxChars="9" valueType="numeric">67890</customer> 
</xml> 

Duyệt qua nó như thế này.

try { 
    $xml = simplexml_load_file("customer.xml"); 

    // Find the customer 
    $result = $xml->xpath('/xml/customer'); 

    $bFirstElement = true; 
    echo  "var customers = {\r\n"; 
    while(list(, $node) = each($result)) { 
     if($bFirstElement) { 
      echo "'". $node."':{\r\n"; 
      $bFirstElement = false; 
     } else { 
      echo ",\r\n'". $node."':{\r\n"; 
     } 

     $bFirstAtt = true; 
     foreach($node->attributes() as $a => $b) { 
      if($bFirstAtt) { 
       echo "\t".$a.":'".$b."'"; 
       $bFirstAtt = false; 
      } else { 
       echo ",\r\n\t".$a.":'".$b."'"; 
      } 
     } 
     echo "}"; 
    } 
    echo "\r\n};\r\n"; 
} catch(Exception $e) { 
    echo "Exception on line ".$e->getLine()." of file ".$e->getFile()." : ".$e->getMessage()."<br/>"; 
} 

Để tạo ra một cấu trúc JSON như thế này

var customers = { 
'69236':{ 
    editable:'true', 
    maxChars:'9', 
    valueType:'numeric'}, 
'12345':{ 
    editable:'true', 
    maxChars:'9', 
    valueType:'numeric'}, 
'67890':{ 
    editable:'true', 
    maxChars:'9', 
    valueType:'numeric'} 
}; 

Cuối cùng, trong kịch bản của bạn, truy cập vào thuộc tính như

WScript.Echo(customers["12345"].editable); 

Chúc may mắn này

7

này đã khiến tôi phát điên trong vài dịp. Khi SimpleXML gặp một nút chỉ có giá trị văn bản, nó sẽ giảm tất cả các thuộc tính. Cách giải quyết của tôi là sửa đổi XML trước khi phân tích bằng SimpleXML. Với một chút biểu thức chính quy, bạn có thể tạo một nút con chứa giá trị văn bản thực tế. Ví dụ, trong trường hợp của bạn, bạn có thể thay đổi XML để:

<customer editable="true" maxChars="9" valueType="numeric"><value>69236<value></customer> 

Một số mã ví dụ giả định rằng chuỗi XML của bạn là trong $ str:

$str = preg_replace('/<customer ([^>]*)>([^<>]*)<\/customer>/i', '<customer $1><value>$2</value></customer>', $str); 
$xml = @simplexml_load_string($str); 

Điều đó sẽ giữ các thuộc tính và tổ giá trị văn bản trong một nút con.

+1

này thất bại nếu có ví dụ một khối CDATA trong phần tử, như vậy:

+0

Đối với tôi, giải pháp được gọi một cách rõ ràng là '-> children()' khi lặp lại đối tượng xml. Nếu không, các thuộc tính đã biến mất. –

3

Tôi nhận thấy đây là một bài đăng cũ, nhưng trong trường hợp nó tỏ ra hữu ích. Phần mở rộng bên dưới giải pháp @ ryanmcdonnell để làm việc trên bất kỳ thẻ nào thay vì thẻ được mã hóa cứng. Hy vọng nó giúp ai đó.

$str = preg_replace('/<([^ ]+) ([^>]*)>([^<>]*)<\/\\1>/i', '<$1 $2><value>$3</value></$1>', $result); 

Các chính khác nhau là nó thay thế /<customer với /<([^ ]+), và sau đó </customer> với </\\1>

mà nói với nó để phù hợp với một phần của tìm kiếm chống lại các yếu tố đầu tiên trong mẫu.

Sau đó, nó chỉ điều chỉnh phần giữ chỗ ($1, $2, $3) để tính đến thực tế là có ba kết quả phù hợp bây giờ thay vì hai.

+1

Điều này cũng không thành công nếu có ví dụ khối CDATA trong phần tử, như sau:

0

Đó là một câu hỏi cũ, nhưng tôi đã tìm thấy một cái gì đó hoạt động gọn gàng - phân tích cú pháp nó thành đối tượng DOMNode.

// $customer contains the SimpleXMLElement 
$customerDom = dom_import_simplexml($customer); 
var_dump($customerDom->getAttribute('numeric')); 

Sẽ hiển thị:

string 'numeric' 
Các vấn đề liên quan