Pertanyaan Anda sangat luas, jawaban terbaik yang bisa saya berikan adalah Anda harus menggunakan beberapa perpustakaan yang ada untuk menyandikan XML daripada menulis sendiri (karena Anda jelas gagal dengan pekerjaan maka kesalahan penyandian XML dilaporkan oleh konsumen XML).
Menggunakan perpustakaan yang ada juga akan memungkinkan Anda untuk menunjukkan masalah sebelumnya. Misalnya. untuk kode berikut, pastikan semua yang Anda dapatkan kembali dari database Anda adalah string yang disandikan UTF-8.
Juga menggunakan kelas klien database yang lebih modern juga akan membantu Anda untuk menuliskan kodenya. Berikut adalah contoh dengan PDO
dan DOMDocument
:
### configuration values
$config = array(
'Database' => array(
'dsn' => 'mysql:dbname=test;host=localhost;charset=utf8',
'user' => 'testuser',
'pass' => 'test',
),
'table_name' => 'config',
'table_fields' => '*',
);
### implement database access
class Database extends PDO
{
public function __construct(array $config = null)
{
$config = $config ? : $GLOBALS['config'][__CLASS__];
parent::__construct($config['dsn'], $config['user'], $config['pass']);
$this->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$this->setAttribute(PDO::ATTR_EMULATE_PREPARES, FALSE);
$this->setAttribute(PDO::ATTR_DEFAULT_FETCH_MODE, PDO::FETCH_ASSOC);
}
}
### setup the datasource ($rows)
$db = new Database();
$rows = $db->query("SELECT $config[table_fields] FROM $config[table_name]");
### setup the XML encoder ($doc)
$doc = new DOMDocument();
$doc->formatOutput = true;
$doc->loadXML("<$config[table_name]s/>");
$doc->encoding = 'utf-8';
### fetch data from the datasource and encode the XML
foreach ($rows as $row) {
$child = $doc->createElement($config['table_name']);
$child = $doc->documentElement->appendChild($child);
foreach ($row as $key => $value) {
$child->appendChild($doc->createElement($key, $value));
}
}
### output XML
header("Content-Type:text/xml");
echo $doc->saveXML();
Lihat bahwa DomDocument
sedang berhati-hati di sini untuk mengkodekan string UTF-8 dengan benar yang dikembalikan dari database. (biasanya) tidak perlu <![CDATA[...]]>
di sini lebih lama lagi. Seperti yang dapat Anda bayangkan, Anda mungkin meletakkan sesuatu di sana yang merusak penyandian XML Anda.
Juga untuk interaksi basis data, sebagian besar kode Anda juga tidak diperlukan, Anda bisa mengulangi baris, jika tidak ada baris, tidak akan ada iterasi. Ini biasanya paling baik diekspresikan dengan Iterator
foreach
konstruksi bahasa dapat beroperasi yang disediakan oleh antarmuka database modern. Secara teknis Anda dapat mengganti $rows
di sini dengan banyak hal lain, seperti iterator yang melewati beberapa tabel satu demi satu.
Selain itu, menggunakan mode kesalahan pengecualian membuat Anda tidak perlu melakukan cek dan die
ada di seluruh basis kode Anda.
Contoh keluarannya adalah:
<?xml version="1.0" encoding="utf-8"?>
<configs>
<config>
<id>1</id>
<option>value for option with ID1</option>
</config>
<config>
<id>2</id>
<option>value for option with ID2</option>
</config>
...
</configs>
Jika Anda masih perlu membuat elemen CDATA, cara kerjanya sama (saya hanya menampilkan sebagian skrip di sini, yang hanya berisi sedikit modifikasi dengan menambahkan bagian CDATA alih-alih nilai turunan):
### fetch data from the datasource and encode the XML
foreach ($rows as $row) {
$child = $doc->createElement($config['table_name']);
$child = $doc->documentElement->appendChild($child);
foreach ($row as $key => $value) {
$child->appendChild($doc->createElement($key))
->appendChild($doc->createCDATASection($value))
;
}
}
Di sini juga, DOMDocument
menangani pengkodean bagian CDATA dengan benar. Sesuatu yang mungkin tidak Anda lakukan.
Masalah potensial yang mungkin masih Anda temui adalah dengan nama tabel atau baris yang nama XML tidak valid
. Tapi kemudian DOMDocument
sebenarnya akan memberi tahu Anda agar Anda tahu saat membuat XML, tidak hanya setelah itu dengan kesalahan penyandian.