أساسيات لغة Solidity: أنواع البيانات والمتغيرات (State Variables)

دقائق القراءة: 5

أساسيات لغة Solidity: أنواع البيانات والمتغيرات (State Variables)

عند الانتقال من فهم مدخل إلى Web3: ما هو البلوكتشين ولماذا يغير شكل الإنترنت والأنظمة المالية؟ إلى بناء عقود ذكية حقيقية، تصبح لغة Solidity هي نقطة الانطلاق الأساسية على شبكات Ethereum والشبكات المتوافقة مع EVM. ومن أهم المفاهيم التي يجب إتقانها مبكراً: أنواع البيانات وكيفية تعريف المتغيرات، خصوصاً State Variables التي تحتفظ بحالة العقد الذكي بشكل دائم على السلسلة.

فهم هذه الأساسيات لا يفيد فقط في كتابة كود صحيح، بل يؤثر مباشرة على الأمان، وقابلية الصيانة، وتكلفة التنفيذ المعروفة باسم Gas Fees. كما أن اختيار نوع بيانات غير مناسب قد يؤدي إلى منطق تجاري معيب أو استهلاك أعلى للتخزين، وهو أغلى جزء تقريباً في دورة حياة كثير من العقود الذكية.

ما المقصود بـ State Variables داخل العقد الذكي؟

المتغيرات من نوع State Variables هي متغيرات تُعرّف داخل جسم العقد الذكي وخارج الدوال، وتُخزَّن في مساحة التخزين الدائم storage. هذا يعني أن قيمتها تبقى محفوظة بين المعاملات المختلفة، ويمكن قراءتها أو تعديلها بحسب صلاحيات العقد ومنطقه البرمجي.

على عكس المتغيرات المحلية داخل الدوال، فإن State Variables تشكّل الحالة العامة للعقد. أمثلة ذلك: مالك العقد، الرصيد المسجل، عدد المستخدمين، أو حالة تفعيل ميزة معيّنة. ولهذا السبب تعد جزءاً محورياً في تصميم أي DApp.

أنواع البيانات الأساسية في Solidity

1) الأعداد الصحيحة: uint و int

النوع uint يُستخدم للأعداد غير السالبة، بينما int يدعم القيم الموجبة والسالبة. افتراضياً، uint تعني uint256، وهو الحجم الأكثر شيوعاً على مستوى EVM.

يمكن أيضاً استخدام أحجام أصغر مثل uint8 أو uint64 عند الحاجة إلى ضغط التخزين، لكن فائدتها الحقيقية تظهر فقط عند ترتيبها بعناية داخل نفس الحزمة التخزينية storage slot.

2) القيم المنطقية: bool

يُستخدم النوع bool لتخزين حالتين فقط: true أو false. وهو مثالي لتتبع حالات بسيطة مثل إيقاف العقد مؤقتاً، أو التأكد من تنفيذ خطوة معيّنة، أو توثيق ما إذا كان مستخدم ما مسجلاً بالفعل.

3) العناوين: address

النوع address يمثل عنوان حساب على الشبكة، سواء كان حساب مستخدم أو عقداً ذكياً. غالباً ما يُستخدم لتخزين عنوان المالك owner أو المستفيد أو المتعامل مع العقد.

إذا كنت قد أنهيت مقال التشفير والمفاتيح: كيف تعمل المحافظ الرقمية (Public & Private Keys) برمجياً؟ فستفهم جيداً كيف يرتبط كل عنوان بمفتاح عام وآلية توقيع المعاملات، وهو ما يفسر اعتماد العقود الذكية على msg.sender للتحقق من هوية الجهة المستدعية.

4) النصوص والبيانات الثنائية: string و bytes

النوع string مخصص للنصوص، بينما bytes يستخدم لتمثيل بيانات ثنائية أو سلاسل بايتات قد تكون أكثر كفاءة في بعض السيناريوهات. تخزين النصوص الطويلة داخل السلسلة مكلف، لذلك يجب التفكير جيداً قبل استخدام string كمتغير حالة دائم.

مثال عملي على تعريف متغيرات الحالة

الآن ننتقل إلى نموذج عملي يوضح كيفية استخدام أشهر الأنواع داخل عقد ذكي بسيط. يمكنك تجربة المثال مباشرة عبر محرر Remix IDE: كتابة ونشر أول عقد ذكي (Smart Contract) على المتصفح مباشرة، أو ربطه لاحقاً بأدوات مثل Hardhat و Ethers.js.

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.20;

contract StateVariablesExample {
    address public owner;
    string public contractName;
    uint256 public counter;
    bool public isActive;

    constructor(string memory _name) {
        owner = msg.sender;
        contractName = _name;
        counter = 0;
        isActive = true;
    }

    function increment() public {
        require(isActive, "Contract is inactive");
        counter += 1;
    }

    function deactivate() public {
        require(msg.sender == owner, "Only owner can deactivate");
        isActive = false;
    }
}

هذا العقد يوضح عدة نقاط مهمة:

  • المتغير owner يخزن عنوان ناشر العقد.
  • المتغير contractName يحتفظ باسم وصفي للعقد.
  • المتغير counter يمثل حالة رقمية قابلة للتحديث.
  • المتغير isActive يتحكم في منطق التنفيذ داخل الدوال.
  • الكلمة public تنشئ تلقائياً دالة قراءة getter لكل متغير.

الفرق بين State Variables والمتغيرات المحلية

المتغير المحلي يُعرّف داخل الدالة، ويعيش فقط أثناء تنفيذها، ثم يختفي بعد انتهاء المعاملة أو الاستدعاء. أما State Variables فتبقى مخزنة على السلسلة وتؤثر على حالة العقد عبر الزمن.

هذا الفرق مهم جداً لأن أي تعديل على حالة العقد يستهلك غازاً أعلى من تنفيذ عمليات مؤقتة في الذاكرة memory. لذلك يجب عدم تحويل كل قيمة إلى متغير حالة إلا إذا كانت هناك حاجة حقيقية لاستمراريتها بين المعاملات.

استخدم State Variables فقط للقيم التي يحتاج العقد للاحتفاظ بها على المدى الطويل. تخزين بيانات غير ضرورية داخل storage يرفع تكلفة Gas ويصعّب صيانة العقد مستقبلاً.

القيم الافتراضية للمتغيرات

في Solidity، كل متغير حالة يملك قيمة افتراضية حتى قبل التهيئة. فمثلاً:

  • uint يبدأ من 0.
  • bool يبدأ من false.
  • address يبدأ بعنوان صفري 0x0000000000000000000000000000000000000000.
  • string تبدأ كسلسلة فارغة.

هذه القيم الافتراضية مفيدة، لكنها قد تتحول إلى مصدر أخطاء منطقية إذا افترض المطور أن التهيئة حدثت بالفعل. لذلك من الأفضل في العقود الحساسة ضبط القيم داخل constructor بوضوح.

نصائح أمنية وعملية عند تصميم المتغيرات

بمجرد البدء في النشر على شبكات الاختبار بعد إعداد بيئة التطوير: تثبيت محفظة MetaMask والاتصال بشبكات الاختبار (Testnets)، ثم تمويل المحفظة عبر الحصول على عملات تجريبية مجانية (Faucet) للبدء في نشر واختبار العقود الذكية، ستلاحظ أن أي قرار في تعريف المتغيرات ينعكس على التجربة الفعلية للعقد أثناء الاختبار.

لا تجعل متغيرات حساسة مثل owner قابلة للتغيير بدون قيود تحقق صارمة. أي خطأ في منطق الصلاحيات Access Control قد يؤدي إلى فقدان السيطرة على العقد أو استغلاله من مهاجمين.

  • اختر نوع البيانات الأصغر فقط عندما تكون مستفيداً فعلياً من تجميع التخزين.
  • استخدم أسماء واضحة مثل totalSupply أو isPaused بدلاً من أسماء مبهمة.
  • لا تخزن بيانات كبيرة على السلسلة إذا كان يمكن الإشارة إليها خارجياً عبر بنية أكثر كفاءة.
  • استخدم require لحماية التعديلات على الحالة قبل تنفيذ أي تحديث فعلي.

خاتمة

إتقان أنواع البيانات في Solidity وفهم طبيعة State Variables هو الخطوة التي تميّز بين كتابة عقد تجريبي بسيط وتصميم عقد ذكي قابل للاعتماد في بيئة حقيقية. فكل متغير داخل العقد ليس مجرد مكان لتخزين قيمة، بل قرار هندسي يؤثر على الأمان، المنطق، واستهلاك الغاز.

كلما أحسنت اختيار النوع المناسب، وحددت ما يجب أن يبقى في storage وما يجب أن يبقى مؤقتاً داخل الدوال، أصبحت عقودك أكثر احترافية وكفاءة. وهذه القاعدة ستظل أساسية في كل ما ستبنيه لاحقاً من رموز Tokens، أنظمة تصويت، أو بروتوكولات مالية لامركزية.

33 comments

اترك تعليقاً

لن يتم نشر عنوان بريدك الإلكتروني. الحقول الإلزامية مشار إليها بـ *