ویژگی تصویر

تابع xml_set_default_handler() در PHP

  /  PHP   /  تابع xml_set_default_handler() در PHP
بنر تبلیغاتی الف
آموزش PHP

تابع xml_set_default_handler() در PHP بخشی از API مبتنی بر Expat برای پردازش SAX-مانند فایل‌های XML است. این تابع یک “دستگیره” (handler) پیش‌فرض تعیین می‌کند تا هر بخشی از ورودی XML که توسط هندلرهای دیگر (مثل element handler یا character data handler) مدیریت نمی‌شود، دریافت و پردازش شود.

چرا از default handler استفاده کنیم؟

  • برای لاگ‌گیری یا دیباگ کردن محتوا و بخش‌هایی از XML که به‌صورت پیش‌فرض پوشش داده نشده‌اند.
  • برای گرفتن بخش‌های خاص شامل اعلان‌ها (declarations)، بخش‌های نامشخص یا مارک‌آپ خام که توسط سایر handlerها دست نخورده باقی می‌ماند.
  • برای پیاده‌سازی پردازش سفارشی روی fragmentهایی که نمی‌خواهید یا نمی‌توانید با element/character handlerها مدیریت کنید.

امضای تابع و پارامترها

تابعxml_set_default_handler
پارامترها
  • $parser (resource): شناسهٔ parser برگرفته از xml_parser_create()
  • $handler (callable): نام یا تابع قابل فراخوانی که باید دو آرگومان بگیرد (parser, data)
مقدار بازگشتیbool — true در صورت موفقیت، false در صورت خطا

نمونه‌ی ساده: دریافت داده‌های پیش‌فرض

<?php
$xml = <<<XML



  Tove
  Jani
  <![CDATA[Some  & data]]>
  

XML;

$parser = xml_parser_create();
xml_set_element_handler($parser, function($p, $name, $attrs){}, function($p, $name){});
xml_set_character_data_handler($parser, function($p, $data){
    // این هندلر فقط متن معمولی داخل تگ‌ها را می‌گیرد
});
xml_set_default_handler($parser, function($p, $data){
    echo "DEFAULT: " . trim($data) . PHP_EOL;
});

if (!xml_parse($parser, $xml, true)) {
    printf("Error: %s at line %dn", xml_error_string(xml_get_error_code($parser)), xml_get_current_line_number($parser));
}

xml_parser_free($parser);
?>

در مثال بالا، اولین handlerهای استاندارد (element و character) به‌صورت خالی تعریف شده‌اند تا فقط default handler بتواند بخش‌هایی مانند DOCTYPE، CDATA یا processing instruction را بگیرد. خروجی نشان می‌دهد چه بخش‌هایی توسط default handler فراخوانی شده‌اند.

توضیح کد

اول، parser ساخته می‌شود. سپس handlerهای معمولی تنظیم می‌شوند اما پیاده‌سازی آن‌ها خالی است تا default handler مسئولیتِ بخش‌های “پیش‌فرض” را نشان دهد. در نهایت xml_parse اجرا شده و هر بخشِ غیرمعمول یا مارک‌آپ خام به تابع default ارسال می‌شود.

رابطه با دیگر handlerها و نکات کاربردی

  • اگر character data handler نصب شده باشد، متن معمولی داخل تگ‌ها معمولاً توسط آن گرفته می‌شود؛ اما default handler برای داده‌هایی که جایی دیگری پردازش نشده‌اند صدا زده می‌شود.
  • default handler می‌تواند شامل نویسه‌هایی از قبیل بخش‌های اعلان DOCTYPE، processing instructionها، بخش‌هایی از DTD و سایر مارک‌آپهایی باشد که در حالت عادی توسط element یا comment handler پوشش داده نشده‌اند.
  • هندلرها باید عملکرد سبک و سریع داشته باشند؛ استفادهٔ سنگین در default handler می‌تواند باعث کاهش کارایی parser شود.

مثال کاربردی: جمع‌آوری تگ‌های ناشناخته

<?php
$xml = 'okvalue';

$parser = xml_parser_create();
$unknowns = [];

xml_set_element_handler($parser,
    function($p, $name, $attrs){
        // عنصرهای شناخته‌شده را اینجا می‌توان هندل کرد
    },
    function($p, $name){
    }
);

xml_set_default_handler($parser, function($p, $data) use (&$unknowns){
    // در این مثال ما به‌دنبال برچسب‌های خام یا نامتعارف می‌گردیم
    if (preg_match_all('/]*)>(.*?)</\1>/s', $data, $m)) {
        foreach ($m[1] as $i => $tag) {
            $unknowns[] = ['tag' => $tag, 'attrs' => trim($m[2][$i]), 'content' => trim($m[3][$i])];
        }
    }
});

xml_parse($parser, $xml, true);
xml_parser_free($parser);

print_r($unknowns);
?>

در این مثال، default handler تلاش می‌کند تگ‌های نامتعارف را از دادهٔ خام استخراج کند و آن‌ها را در آرایهٔ $unknowns ذخیره کند. توجه کنید که پردازش این‌چنینی با regex برای XML ایده‌آل نیست اما نمونه‌ای از نحوهٔ استفادهٔ pragmatical از default handler است.

ملاحظات امنیتی و جایگزین‌ها

  • اگر XML را از منبع ناآشنا دریافت می‌کنید، به خطرات XXE (External Entity Injection) توجه کنید. API مبتنی بر Expat در PHP به‌طور پیش‌فرض entityهای خارجی را لود نمی‌کند، اما مراقبت‌های اضافی در خواندن فایل‌ها و پارس کردن لازم است.
  • برای پردازش پیچیده‌تر یا تغییرات ساختاری، استفاده از DOMDocument یا XMLReader ممکن است مناسب‌تر و ایمن‌تر باشد؛ آن‌ها کنترل بیشتر و قابلیت‌های مدرن‌تری دارند.
  • default handler برای عملیات‌های دیباگ، لاگ‌گیری یا جمع‌آوری بخش‌های غیرمعمول مفید است؛ اما برای استخراج دقیق داده‌ها بهتر است element و character handlers را به‌طور مشخص تنظیم کنید.

خلاصه و پیشنهادات عملی

xml_set_default_handler() یک ابزار مفید در مجموعه توابع XMLِ PHP است که به شما اجازه می‌دهد هر محتوای غیرمعمول یا نادیده گرفته‌شده توسط سایر handlerها را دریافت و پردازش کنید. این تابع مناسب دیباگ، لاگ‌گیری و پردازش fragmentهای خاص است، اما برای پردازش ساختاری و دقیق XML، ترکیب آن با element/character handlers یا استفاده از XMLReader/DOM توصیه می‌شود.

در نهایت، همواره به کارایی و امنیت فکر کنید: handlerها را سبک نگه دارید، از پردازش‌های سنگین داخل callbackها پرهیز کنید و هرگاه نیاز به پردازش پیچیده‌تر داشتید از ابزارهای مناسب‌تری بهره ببرید.

آیا این مطلب برای شما مفید بود ؟

خیر
بله
موضوعات شما در انجمن: