تعلم أساسيات React في 10 دقائق: دليلك الشامل للمبتدئين

دقائق القراءة: 9
إذا كنت تتطلع لتعلم أساسيات مكتبة React الشهيرة في الوقت الذي تستغرقه لاحتساء فنجان قهوة، فهذا المقال هو دليلك الأمثل. نهدف هنا إلى تقديم مقدمة سهلة للمبتدئين حول React: ماهيته، ولماذا أصبح ضرورة في عالم تطوير الويب الحديث. يفترض هذا المقال أن لديك فهماً أساسياً للغة JavaScript. سنتعمق في استكشاف بعض مفاهيمه الأساسية، وما الذي يمكنك بناؤه باستخدامه، وسنستعرض بعض الأمثلة البرمجية. الهدف الأسمى هو اكتساب فهم بديهي وشامل لجوهر React، مما يجعلك مرتاحاً للتعامل مع أساسياته.

ما هو React؟

تطورت مكتبة React على يد شركة Facebook في عام 2011، وسرعان ما أصبحت واحدة من أكثر مكتبات JavaScript استخداماً على نطاق واسع في بناء واجهات المستخدم. تُظهر الإحصائيات، مثل تلك الصادرة عن HackerRank، أن 30% من أصحاب العمل يبحثون عن مطورين يمتلكون معرفة بـ React، بينما يمتلك نصف المتقدمين فقط المعرفة المطلوبة. من الواضح أن React يحظى بطلب كبير في سوق العمل.

فما هو React تحديداً؟ إنه مكتبة JavaScript فعالة ومرنة مصممة لبناء واجهات المستخدم (UIs)، و React نفسه مكتوب باستخدام JavaScript. يتميز React بقدرته على تقسيم واجهات المستخدم المعقدة إلى أجزاء صغيرة ومعزولة من التعليمات البرمجية تُعرف باسم “المكونات” (Components). من خلال استخدام هذه المكونات، يركز React فقط على ما يراه المستخدم على الواجهة الأمامية للموقع.

توضيح لمكونات React في تطبيق حاسبة، حيث يتم تقسيم الواجهة إلى أجزاء مستقلة.

المكونات: حجر الزاوية في React

المكونات هي وحدات مستقلة وقابلة لإعادة الاستخدام. يمكن أن تكون إما دوال JavaScript (JavaScript functions) أو فئات (classes). في كلتا الحالتين، تقوم بإرجاع جزء من التعليمات البرمجية يمثل جزءاً من صفحة الويب. إليك مثال على مكون دالة (function component) يقوم بعرض عنصر <h2> على الصفحة:

function Name() {
  return <h2>Hi, my name is Joe!</h2>;
}

وهنا مثال على مكون فئة (class component) يقوم بنفس عملية العرض:

class Person extends React.Component {
  render() {
    return <h2>Hi again from Joe!</h2>;
  }
}

يتطلب استخدام مكون الفئة جهداً أكبر قليلاً، حيث يتعين عليك تمديد (extend) الفئة React.Component (وهي جزء من مكتبة React)، بينما مكون الدالة هو في الغالب مجرد JavaScript عادي. ومع ذلك، توفر مكونات الفئات وظائف حاسمة تفتقر إليها مكونات الدوال (لمزيد من التفاصيل، راجع Functional vs Class-Components in React).

JSX: مزيج HTML و JavaScript

ربما لاحظت وجود مزيج غريب من HTML و JavaScript داخل كل مكون. يستخدم React في الواقع لغة تُعرف باسم JSX، والتي تسمح بخلط HTML مع JavaScript. لا يمكنك استخدام JSX لإرجاع عناصر HTML معرفة مسبقاً فحسب، بل يمكنك أيضاً إنشاء عناصرك الخاصة. على سبيل المثال، بدلاً من عرض عناصر <h2> مباشرة في مكون الفئة، يمكنك عرض المكون الوظيفي الذي يُرجع نفس الشيء:

class Person extends React.Component {
  render() {
    return <Name />;
  }
}

لاحظ علامة الإغلاق الذاتي ‘/>‘ للمكون. تبدأ قوة React في الظهور بوضوح عندما تتخيل إمكانية عرض العديد من المكونات البسيطة لتشكيل مكون أكثر تعقيداً. لبناء صفحة، يمكننا استدعاء هذه المكونات بترتيب معين، واستخدام النتائج التي تُرجعها، وعرضها للمستخدم.

لماذا نختار React بدلاً من JavaScript الخام (Vanilla JS)؟

إن القدرة على تقسيم واجهات المستخدم المعقدة من خلال استخدام المكونات تمنح React ميزة واضحة على Vanilla JavaScript (وهو JavaScript عادي بدون أي مكتبات أو أطر عمل خارجية). ولكن ما الذي يمكن أن يفعله React أيضاً ليجعله مطلوباً بهذا الشكل بين أصحاب العمل؟ دعنا نلقي نظرة على الاختلافات في كيفية تعامل React و Vanilla JS مع الأمور.

في القسم السابق، ناقشنا كيف يستخدم React المكونات لعرض واجهات المستخدم. لم نتعمق في ما كان يحدث على جانب HTML. قد يكون من المفاجئ معرفة أن كود HTML الذي يترافق مع React بسيط حقاً:

<div id="root"></div>

عادة ما يكون مجرد عنصر <div> مع معرف (id) يعمل كحاوية لتطبيق React. عندما يقوم React بعرض مكوناته، فإنه يبحث عن هذا المعرف للعرض فيه. تكون الصفحة فارغة قبل هذا العرض.

من ناحية أخرى، يحدد Vanilla JS واجهة المستخدم الأولية مباشرة في HTML. بالإضافة إلى ذلك، يتولى Vanilla JS مهمة الوظائف، بينما يتولى HTML مهمة عرض المحتوى (الترميز). في الأيام الأولى للويب، بدا فصل الوظائف والترميز منطقياً لأن التطبيقات كانت أبسط. ومع ذلك، مع تزايد التعقيد، تزايدت أيضاً المشاكل المتعلقة بصيانة أجزاء كبيرة من كود JS. يمكن أن ينتشر كود JS الذي يقوم بتحديث جزء من HTML عبر عدة ملفات، وقد يجد المطورون صعوبة في تتبع مصدر الكود. يجب عليهم تذكر جميع التفاعلات بين الكود الموجود في ملفات مختلفة.

تبسيط إدارة DOM باستخدام React

يقوم React بفرز الكود إلى مكونات، حيث يحتفظ كل مكون بجميع الكود اللازم لعرض وتحديث واجهة المستخدم. يتطلب تحديث واجهة المستخدم تحديث DOM، أو نموذج كائن المستند (document object model). وهنا تكمن قوة React الحقيقية. إذا كنت ترغب في الوصول إلى DOM في Vanilla JS، يجب عليك أولاً العثور عليه قبل أن تتمكن من استخدامه. يقوم React بتخزين البيانات في متغيرات JS عادية ويحتفظ بنموذج DOM افتراضي خاص به (Virtual DOM). إذا كنت ترغب بعد ذلك في تحديث DOM في Vanilla JS، يجب عليك تحديد العقدة المناسبة ثم إضافة أو إزالة العناصر يدوياً. أما React فيقوم بتحديث واجهة المستخدم تلقائياً بناءً على حالة التطبيق (application state)، وهو ما سنناقشه بمزيد من التفصيل في القسم التالي.

لذلك، يمكن تلخيص السبب الرئيسي وراء رغبتنا في استخدام React بدلاً من Vanilla JS في كلمة واحدة: البساطة. مع Vanilla JS، من السهل أن تضيع في متاهة من عمليات البحث والتحديثات في DOM. يجبرك React على تقسيم تطبيقك إلى مكونات، مما ينتج عنه كود أكثر قابلية للصيانة. وبالتالي، بالنسبة للتطبيقات المعقدة، ستحتاج بالتأكيد إلى تعلم React.

مفاهيم React الأساسية

لقد ناقشنا بالفعل كيف يستخدم React المكونات لتقسيم واجهات المستخدم المعقدة، و JSX لعرض هذه المكونات. في هذا القسم، سنتحدث عن بعض المفاهيم الأساسية الأخرى في React.

الحالة (State)

كما ذكرنا سابقاً، يقوم React بتحديث واجهة المستخدم بناءً على حالة التطبيق. يتم تخزين هذه الحالة فعلياً كخاصية لمكون فئة React:

class Counter extends React.Component {
  state = { value: 0 };
}

لنفترض أن لدينا عداداً وزرين يزيدان القيمة أو ينقصانها. يتم عرض قيمة العداد على الصفحة عبر JSX. تعتمد قيمة العداد المعروضة على الحالة، ونقوم بتغيير الحالة بالنقر على أحد الأزرار. يتعامل Vanilla JS مع نقرة الزر كحدث، وكذلك React. عند حدوث مثل هذا الحدث، سنقوم باستدعاء دوال تزيد أو تنقص العداد بناءً على الزر الذي تم النقر عليه. تحتوي هذه الدوال على الكود الذي يغير حالة المكون. إليك مثال على هذا العداد:

class Counter extends React.Component {
  state = { value: 0 };

  handleIncrement = () => {
    this.setState(state => ({
      value: state.value + 1
    }));
  };

  handleDecrement = () => {
    this.setState(state => ({
      value: state.value - 1
    }));
  };

  render() {
    return (
      <div>
        <p>{this.state.value}</p>
        <button onClick={this.handleDecrement}>Decrement</button>
        <button onClick={this.handleIncrement}>Increment</button>
      </div>
    );
  }
}

لقد قمنا بتحديث الحالة عن طريق استدعاء الدالة setState() في كل دالة من الدوال التي تتعامل مع نقرة الزر. سيتم تحديث العداد المعروض على الصفحة في الوقت الفعلي. وهكذا، اكتسب React اسمه لأنه “يتفاعل” (reacts) مع تغييرات الحالة. باختصار، يراقب React تلقائياً حالة كل مكون بحثاً عن التغييرات ويحدث DOM بشكل مناسب.

الخصائص (Props)

يمكننا استخدام props (اختصار لـ “properties” أو الخصائص) للسماح للمكونات بالتواصل مع بعضها البعض. لنفترض أن العداد في مثالنا السابق يمثل كمية منتج يرغب العميل في شرائه. يريد المتجر تحديد حد أقصى للمنتجات المشتراة لكل عميل بمنتجين. عند الدفع، نريد عرض رسالة مناسبة إذا حاول العميل شراء أكثر من منتجين. إليك كيف يمكننا القيام بذلك باستخدام props:

const Display = (props) => {
  let message;
  if (props.number > 2) {
    message = 'أنت مقيد بشراء منتجين كحد أقصى!';
  } else {
    message = 'كل شيء على ما يرام.';
  }
  return (<p>{message}</p>);
};

class Timer extends React.Component {
  state = { quantity: 0 }
  //... كود للتعامل مع النقر على الأزرار، تحديث الحالة، إلخ.
  render(){
    return(
      <div>
        <Display number={this.state.quantity} />
        {/* ... كود للمكونات الأخرى */}
      </div>
    );
  }
}

نقوم بإنشاء مكون دالة يسمى Display ونمرر props كمعامل. عندما نقوم بعرض هذا المكون، نمرر له number كخاصية مضبوطة على كمية المنتج الذي يرغب العميل في شرائه. هذا مشابه لتعيين خاصية لعنصر HTML. نستدعي هذه القيمة باستخدام props.number داخل المكون Display لتحديد الرسالة التي سيتم إرجاعها.

دورة حياة المكون (Component Lifecycle)

بينما يقوم React بتحديث DOM بناءً على حالات المكونات، توجد دوال خاصة تسمى “دوال دورة الحياة” (lifecycle methods) لتوفير فرص لتنفيذ إجراءات في نقاط محددة من دورة حياة المكون. تسمح لك هذه الدوال بالتعامل مع المكونات في نقطة زمنية معينة لاستدعاء دوال مناسبة. يمكن أن تكون هذه النقاط الزمنية قبل عرض المكونات، أو بعد تحديثها، وما إلى ذلك. قد ترغب في استكشاف دوال دورة حياة المكونات بمزيد من التفصيل.

لرؤية دوال دورة الحياة عملياً، يمكنك الاطلاع على ساعة Pomodoro Clock التي أنشأتها. يتم ضبط مؤقت الساعة في البداية على طول الجلسة. عندما ينتهي عداد الجلسة إلى الصفر، يجب أن يتحول المؤقت إلى طول الاستراحة ويبدأ العد التنازلي من هناك. نظراً لأن المؤقت هو مكون، فقد استخدمت دالة دورة الحياة componentDidUpdate() ضمن مكون الفئة الرئيسي الخاص بي للتعامل مع أي تغييرات باستخدام handleChange():

componentDidUpdate() {
  this.handleChange();
}

يمكنك التفكير في دوال دورة الحياة كإضافة مستمعي أحداث (event listeners) في Vanilla JS إلى مكون React.

ماذا يمكنك أن تبني باستخدام React؟

الآن بعد أن أصبح لديك فهم أساسي لـ React، ما الذي يمكنك بناؤه به؟ لقد ذكرنا بالفعل في بداية هذا المقال أن Facebook طورت React في عام 2011، لذا فمن الطبيعي أن تكون منصة Facebook مبنية على React. تشمل التطبيقات الشهيرة الأخرى التي تستخدم React كلياً أو جزئياً: Instagram، Netflix، و WhatsApp.

لكن كمبتدئين في React، لا نتطلع إلى بناء Facebook التالي على الفور، لذا إليك قائمة بـ “10 React Starter Project Ideas to Get You Coding“. إذا كنت ترغب في معرفة المزيد عن تطوير الويب والاطلاع على بعض الأمثلة لمشاريع React سهلة للمبتدئين، تفضل بزيارة مدونتي على 1000 Mile World.

شكراً للقراءة ونتمنى لكم برمجة سعيدة!

الخلاصة التقنية

لقد أثبتت مكتبة React نفسها كأداة لا غنى عنها في تطوير واجهات المستخدم الحديثة، وذلك بفضل نهجها المبتكر القائم على المكونات. إن قدرتها على تبسيط إدارة DOM عبر مفهوم Virtual DOM، وتوفير بنية واضحة لإدارة الحالة والخصائص، تجعلها الخيار الأمثل لبناء تطبيقات ويب معقدة وقابلة للصيانة. من خلال فصل الاهتمامات وتغليف المنطق والعرض داخل مكونات مستقلة، يقلل React بشكل كبير من التعقيد الذي يواجهه المطورون عند التعامل مع تطبيقات JavaScript كبيرة. هذا التركيز على الكفاءة وقابلية التوسع هو ما يضمن استمرار React في صدارة اهتمامات المطورين والشركات على حد سواء.

اترك تعليقاً

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