ویژگی تصویر

آموزش Serialize و Unserialize — تبدیل داده‌ها برای ذخیره و انتقال

  /  PHP   /  آموزش Serialize و Unserialize
بنر تبلیغاتی الف
آموزش PHP

Serializing و Unserializing مفاهیمی پایه در توسعهٔ نرم‌افزار هستند که به معنی تبدیل ساختارهای داده (مثلاً آرایه‌ها، اشیاء) به یک قالب قابل ذخیره یا انتقال و سپس بازسازی دوبارهٔ آن‌هاست. در این مقاله به صورت عملیاتی، مثال‌ها، مقایسه‌ها و نکات امنیتی و بهینه‌سازی را بررسی می‌کنیم.

چرا Serialize مهم است؟

  • ذخیره کردن وضعیت یک شیء در دیتابیس یا فایل
  • ارسال داده بین سرویس‌ها (RPC، پیام‌رسانی، API)
  • کش کردن داده‌های پیچیده در حافظه مثل Redis یا Memcached
  • قابلیت بازسازی مجدد اشیاء در زمان اجرا

فرمت‌های رایج

چند قالب پرکاربرد برای serialization عبارت‌اند از: JSON، XML، Binary (مثل PHP serialize یا Java Serializable)، Protocol Buffers، MessagePack. هر کدام مزایا و معایب خود را دارند: JSON قابل خواندن است ولی نوع‌های پیچیده (مثل اشیاء با متد) را حفظ نمی‌کند؛ باینری سریع‌تر و فشرده‌تر است ولی قابل خواندن نیست.

فرمتمزایامعایب
JSONقابل خواندن، رایج، امن‌تر برای دادهٔ سادهحفظ نوع و متدهای شیء مشکل‌ساز
PHP serializeمی‌تواند اشیاء PHP را بازسازی کندمشکل امنیتی روی دادهٔ ناشناخته، بزرگ‌تر از JSON
Protocol Buffersسریع و فشرده، schema-basedنیاز به تعریف schema و کامپایل

مثال عملی در PHP: serialize و unserialize

id = $id;
        $this->name = $name;
    }
}
$user = new User(1, "Ali");
$serialized = serialize($user);
$restored = unserialize($serialized);
var_dump($serialized);
var_dump($restored);
?>

توضیح: این کد یک شیء User می‌سازد، آن را با serialize به رشته تبدیل می‌کند و سپس با unserialize دوباره شیء را بازسازی می‌کند. serialize اطلاعات نام کلاس و خصوصیات را در قالبی خاص ذخیره می‌کند. این روش برای ذخیرهٔ وضعیت شیء در فایل یا دیتابیس کاربرد دارد.

خطرات امنیتی در PHP و راه‌های امن‌تر

اجرای unserialize روی دادهٔ ورودی از منبع غیرقابل اعتماد می‌تواند منجر به Remote Code Execution یا Object Injection شود. بنابراین از unserialize روی دادهٔ کاربر استفاده نکنید یا از گزینهٔ امن PHP بهره ببرید.

 false]);
if ($object === false && $data !== 'b:0;') {
    // handle invalid data
}
?>

توضیح: در این مثال، با پارامتر allowed_classes=>false از بازسازی هر گونه شیء جلوگیری می‌کنیم و فقط ساختارهای اسکالر و آرایه‌ها بازسازی می‌شوند. همچنین بررسی مقدار بازگشتی برای شناسایی دادهٔ نامعتبر مهم است.

جایگزین امن: JSON

 1, 'name' => 'Ali'];
$json = json_encode($array);
$restored = json_decode($json, true);
// json_decode با true آرایهٔ associative برمی‌گرداند
?>

توضیح: JSON برای انواع ساده بسیار مناسب و امن‌تر است. json_encode و json_decode برای انتقال بین زبان‌ها و ذخیره‌سازی دادهٔ ساده توصیه می‌شوند. اما JSON نمی‌تواند متدهای کلاس‌ها را حفظ کند.

مثال در Python: pickle و جایگزینی امن

import pickle
data = {'id': 1, 'name': 'Ali'}
serialized = pickle.dumps(data)
restored = pickle.loads(serialized)
print(serialized)
print(restored)

توضیح: pickle می‌تواند هر شیءٔ پایتون را سریالایز کند اما مانند unserialize پی‌اچ‌پی برای دادهٔ ناشناس ناامن است. در کاربردهای بین‌زبان یا دادهٔ ساده بهتر است از JSON (با json.dumps / json.loads) استفاده شود.

بهینه‌سازی و نکات عملکرد

  • برای حجم داده زیاد از فرمت‌های باینری فشرده (MessagePack، Protocol Buffers) استفاده کنید.
  • برای کشینگ در Redis، بررسی اندازهٔ سریالایز شده مهم است—استفاده از igbinary در PHP می‌تواند حجم را کاهش دهد.
  • در صورت سریالایز کردن مکرر، از پیش‌پردازش schema یا استفاده از serializer سریع (مثلاً avro/protobuf) بهره ببرید.
  • استفاده از streaming serialization برای داده‌های بزرگ جهت جلوگیری از مصرف حافظهٔ زیاد.

چه زمانی از serialization اشیاء استفاده کنیم؟

در سیستم‌هایی که نیاز به حفظ وضعیت کامل اشیاء بین درخواست‌ها دارید (مثلاً session persistence، job queues که اشیاء کار را نگه می‌دارند)، serialization اشیاء مفید است. در سیستم‌های API بین‌زبان یا ذخیرهٔ داده‌های ساده، معمولاً JSON یا یک format schema-based مناسب‌تر است.

نکات عملی و best practices

  • هرگز دادهٔ ناشناخته را با unserialize/pickle مستقیم بارگذاری نکنید.
  • اگر مجبور به استفاده از unserialize هستید، پارامترهای امن مثل allowed_classes را اعمال کنید یا از کتابخانه‌هایی با sandbox استفاده کنید.
  • برای ارتباط بین سرویس‌ها از formatهای استاندارد و قابل نسخه‌بندی (versioned schemas) استفاده کنید تا تغییرات ساختار به درستی مدیریت شوند.
  • اندازهٔ دادهٔ سریالایز شده را بسنجید و در صورت لزوم از فشرده‌سازی (gzip) استفاده کنید.

خلاصه و جمع‌بندی

Serialize و Unserialize ابزارهای قدرتمندی برای ذخیره و انتقال وضعیت برنامه‌ها هستند اما همراه با خطرات و محدودیت‌هایی می‌آیند. انتخاب فرمت مناسب (JSON، باینری، schema-based) و رعایت نکات امنیتی و عملکردی، کلید استفادهٔ صحیح از آن‌ها است. همیشه از راهکارهای امن و استاندارد استفاده کنید و در موقعیت‌هایی که امکان دارد از JSON یا فرمت‌های schema-based که بین زبان‌ها قابل‌اعتمادند بهره ببرید.

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

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