استخدام مكتبة عميل JavaScript (الإصدار 2.0)

تحذير: تتعلق هذه الصفحة بواجهات برمجة التطبيقات القديمة من Google، وهي واجهات برمجة التطبيقات لبيانات Google؛ وهي مرتبطة فقط بواجهات برمجة التطبيقات المدرجة في دليل Google Data APIs، والتي تم استبدال العديد منها بواجهات برمجة تطبيقات أحدث. للحصول على معلومات حول واجهة برمجة تطبيقات جديدة، اطلع على وثائق واجهة برمجة التطبيقات الجديدة. للحصول على معلومات حول تفويض الطلبات باستخدام واجهة برمجة تطبيقات أحدث، اطلع على مصادقة حسابات Google وتفويضها.

يصف هذا المستند كيفية استخدام مكتبة عميل JavaScript لإرسال طلبات بحث في Google Data API وتفسير الاستجابات المعروضة.

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

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

الجمهور

تم إعداد هذا المستند لمبرمجي جافا سكريبت الذين يريدون كتابة تطبيقات عميل يمكنها التفاعل مع خدمات بيانات Google.

يفترض هذا المستند أنك تفهم الأفكار العامة وراء بروتوكول Google Data APIs. كما يفترض أيضًا أنك تعرف كيفية البرمجة باستخدام جافا سكريبت.

للحصول على معلومات مرجعية حول الفئات والطرق المتاحة من خلال مكتبة العميل، اطلع على مرجع واجهة برمجة تطبيقات مكتبة عميل جافا سكريبت (بتنسيق JSdoc).

تم تصميم هذا المستند للقراءة بالترتيب، ويعتمد كل مثال على الأمثلة السابقة.

بنود الاستخدام

أنت توافق على الالتزام ببنود استخدام مكتبة عميل "جافا سكريبت من Google" عند استخدام "مكتبة عميل JavaScript".

نظرة عامة على نموذج البيانات وتدفق التحكم

تستخدم مكتبة عميل JavaScript مجموعة من الفئات لتمثيل العناصر المستخدمة في Google Data APIs.

ملاحظة: التمثيل الأساسي للبيانات هو JSON، ولكن توفّر مكتبة العميل طبقة تجريدية حتى لا تضطر إلى التعامل مع بيانات JSON مباشرةً. إذا كنت ترغب في العمل مع JSON مباشرةً، بدون مكتبة العميل، راجع استخدام JSON مع واجهات برمجة التطبيقات لبيانات Google.

توفر المكتبة طرقًا تتيح لك إرسال البيانات بشكل غير متزامن إلى الخدمة التي تحتوي على واجهة برمجة تطبيقات للبيانات واستلامها. على سبيل المثال، ترسل طريقة google.gdata.calendar.CalendarService.getEventsFeed() طلبًا للحصول على خلاصة إلى "تقويم Google". إن إحدى المعلّمات التي تمرِّرها هي دالة متابعة، وتُعرف أيضًا باسم معاودة الاتصال، وتعرض الخدمة الخلاصة بتنسيق JSON، من خلال استدعاء وظيفة المتابعة. ويمكن للعميل بعد ذلك استدعاء العديد من طرق get لاستخدام البيانات في شكل كائنات JavaScript.

لإضافة إدخال جديد، يمكنك إنشاء الإدخال باستخدام فئات مكتبة العميل وأساليبه، ثم استدعاء طريقة feed.insertEntry() لإرسال الإدخال الجديد إلى الخدمة. ومرة أخرى يمكنك توفير دالة متابعة، والتي تستدعيها الخدمة عند إضافة الإدخال بنجاح.

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

للحصول على مزيد من المعلومات حول نمط البرمجة هذا، اطلع على "نمط التمرير المستمر" في ويكيبيديا.

لمحة عن البيئات المتوافقة

لا ندعم حاليًا سوى تطبيقات عميل جافا سكريبت التي تعمل في صفحة ويب في المتصفح. المتصفحات المتوافقة حاليًا هي:

  • فايرفوكس 2.x و3.x
  • Internet Explorer 6 و7 و8
  • الإصدار 3.x و 4.x من Safari
  • Google Chrome (كل الإصدارات)

تعالج مكتبة عميل JavaScript جميع عمليات الاتصال بخادم الخدمة. إذا كنت مطوّر برامج JS متمرّسًا، قد تفكر في طرح عبارة "ولكن ماذا عن سياسة المصدر نفسه؟" تتيح مكتبة عميل JavaScript للعميل إرسال طلبات "بيانات Google" من أي نطاق مع الالتزام بنموذج أمان المتصفّح.

للحصول على نظرة عامة حول المصادقة باستخدام واجهات برمجة التطبيقات لبيانات Google، يمكنك الاطِّلاع على نظرة عامة على مصادقة Google Data APIs. يفترض بقية هذا المستند أنك على دراية بأساسيات آلية عمل هذا النظام.

نماذج تطبيقات العملاء

للاطلاع على مكتبة عميل جافا سكريبت بشكل عملي، انتقل إلى صفحة النماذج.

البرنامج التعليمي والأمثلة

توضح الأمثلة التالية كيفية إرسال طلبات متعددة لواجهة برمجة التطبيقات باستخدام مكتبة عميل JavaScript.

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

جارٍ تحميل المكتبة

قبل أن يتمكن العميل من استخدام مكتبة العميل، يجب أن يطلب رمز مكتبة البرنامج من الخادم.

يمكنك البدء باستخدام علامة <script> في القسم <head> من مستند HTML لجلب أداة تحميل Google AJAX API:

<script type="text/javascript" src="https://www.google.com/jsapi"></script>

يمكنك تصغير جولات الذهاب والإياب إلى خوادم Google وخفض وقت الاستجابة من خلال التحميل المسبق للمكتبة. لتحميل حزم معيّنة مسبقًا مباشرةً من أداة تحميل واجهة برمجة تطبيقات Google AJAX (بدون استخدام google.load()، يمكنك الاطّلاع أدناه):

<script type="text/javascript"
      src="https://www.google.com/jsapi?autoload=%7Bmodules%3A%5B%7Bname%3Agdata%2Cversion%3A2.x%2Cpackages%3A%5Bblogger%2Ccontacts%5D%7D%5D%7D"></script>

ملاحظة: يجب ترميز عنوان URL src للنص البرمجي بالكامل. على سبيل المثال، المثال السابق هو
<script type="text/javascript" src="https://www.google.com/jsapi?autoload={modules:[{name:gdata,version:2.x,packages:[blogger,contacts]}]}"></script>.

في حال عدم تحميل الوحدات تلقائيًا، يمكنك تحميل مكتبة برامج "بيانات Google" باستخدام المثال التالي في رمز إعداد JavaScript، بعد جلب أداة التحميل الشائعة. يجب إجراء هذه المكالمة من القسم <head> في مستند HTML الخاص بك (أو من ملف JavaScript مضمّن باستخدام علامة <script> في القسم <head> من مستند HTML):

google.load("gdata", "2");

وبدلاً من ذلك، يمكنك طلب خدمات معينة بدلاً من المكتبة بأكملها. ينزّل المثال التالي حزم Blogger وجهات الاتصال فقط:

google.load("gdata", "2.x", {packages: ["blogger", "contacts"]});

المعلمة الثانية لـ google.load() هي رقم الإصدار المطلوب من مكتبة عميل JavaScript.تم تصميم مخطط ترقيم الإصدار وفقًا للإصدار الذي تستخدمه واجهة برمجة التطبيقات لخرائط Google. في ما يلي أرقام الإصدارات المحتملة ومعناها:

"1"
النسخة الثانية إلى الأخيرة من الإصدار الرئيسي 1.
"1.x"
أحدث نسخة من الإصدار الرئيسي 1.
"1.s"
أحدث إصدار ثابت من الإصدار الرئيسي 1. سنعلن من حين لآخر إصدارًا معينًا من مكتبة البرنامج ليكون "ثابتًا" استنادًا إلى التعليقات التي تصلنا من مطوّري البرامج. ومع ذلك، قد لا يحتوي هذا الإصدار على أحدث الميزات.
"1.0"، "1.1 بوصة، إلخ
إصدار معيّن من المكتبة، يتضمّن رقم مراجعة رئيسيًا وثانويًا محدّدًا

بعد استدعاء google.load()، يجب أن تطلب من القائم بالتحميل الانتظار حتى انتهاء تحميل الصفحة ثم استدعاء الرمز:

google.setOnLoadCallback(getMyFeed);

حيث getMyFeed() هي دالة محددة في القسم التالي من هذا المستند. استخدِم هذا الأسلوب بدلاً من إرفاق معالج onload بالعنصر <body>.

طلب خلاصة لم تتم مصادقتها

لطلب خلاصة لم تتم مصادقتها، أضِف الرمز التالي إلى ملف JavaScript أو إلى علامة <script> في ملف HTML.

في الرمز التالي، يتم استدعاء getMyFeed() أولاً (بواسطة أداة تحميل واجهة برمجة تطبيقات AJAX، كما هو موضح في القسم السابق).

تستدعي الدالة setupMyService() لإنشاء اتصال (يمثله كائن CalendarService) إلى تقويم Google. لقد سحبنا رمز إنشاء الخدمة إلى دالة منفصلة للوحدات النمطية؛ في وقت لاحق، سنُعدِّل الدالة setupMyService()، بناءً على خيارات المصادقة التي تختارها.

بعد إعداد الخدمة، يستدعي getMyFeed() طريقة getEventsFeed() في مكتبة العميل لطلب الخلاصة.

ونحن بصدد تحديد عنوان URL للخلاصة في متغيّر عام حتى يمكن استخدامه في الدوال اللاحقة. في هذا المثال، نستخدم عنوان URL للخلاصة العامة (لم تتم المصادقة عليها) لمستخدم يُسمّى liz@gmail.com. يمكنك أيضًا استخدام default بدلاً من عنوان البريد الإلكتروني للمستخدم لتمثيل المستخدم الذي تمت المصادقة عليه.

var feedUrl = "http://www.google.com/calendar/feeds/liz@gmail.com/public/full";

function setupMyService() {
  var myService = new google.gdata.calendar.CalendarService('exampleCo-exampleApp-1');
  return myService;
}

function getMyFeed() {
  myService = setupMyService();

  myService.getEventsFeed(feedUrl, handleMyFeed, handleError);
}

وتجدر الإشارة إلى أننا سنجعل myService متغيّرًا عموميًا لتيسير استخدامه في الدوال اللاحقة.

لتشغيل الرمز أعلاه في البرنامج الخاص بك، يجب استخدام عنوان بريد إلكتروني حقيقي لمستخدم، لحساب تقويم يتضمن تقويمًا مشتركًا بشكل عام.

ملاحظة: عند إنشاء كائن CalendarService جديد، تستدعي مكتبة العميل طريقة باسم google.gdata.client.init()، والتي تتحقق من أن المتصفِّح الذي يتم تشغيل البرنامج متوافق معه. إذا كان هناك خطأ، فستعرض مكتبة العميل رسالة خطأ للمستخدم. إذا كنت تريد معالجة هذا النوع من الأخطاء بنفسك، يمكنك عندئذٍ استدعاء google.gdata.client.init(handleInitError) بشكل صريح قبل إنشاء الخدمة، حيث يكون handleInitError() هو وظيفتك. إذا حدث خطأ في Init، فستحصل الدالة على كائن خطأ قياسي، ويمكنك إجراء أي شيء تريده بهذا الكائن.

في الاستدعاء إلى getEventsFeed()، الوسيطة الثانية هي handleMyFeed، وهي عبارة عن وظيفة رد اتصال، انظر أدناه. يعالج تقويم Google الطلب، ثم يمرر، في حالة نجاح الطلب، كائن "جذر الخلاصة" الذي يحتوي على الخلاصة المطلوبة إلى رد الاتصال. جذر الخلاصة هو عبارة عن كائن حاوية يحتوي على خلاصة.

الوسيطة الثالثة لـ getEventsFeed() هي دالة اختيارية لمعالجة الأخطاء، وفي حالة مواجهة مكتبة العميل لخطأ، فإنها تستدعي معالج الخطأ المحدد بدلاً من دالة رد الاتصال الناجحة. الكائن الذي تمرره مكتبة العميل كوسيطة إلى معالج الأخطاء هو مثال على كائن JavaScript Error، مع خاصية cause إضافية.

إليك إصدارات بسيطة من وظيفة رد الاتصال ومعالج الأخطاء:

function handleMyFeed(myResultsFeedRoot) {
  alert("This feed's title is: " + myResultsFeedRoot.feed.getTitle().getText());
}

function handleError(e) {
  alert("There was an error!");
  alert(e.cause ? e.cause.statusText : e.message);
}

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

ملاحظة: بما أنّ هذا الرمز لا يُجري المصادقة، يمكنك استخدامه للحصول على خلاصة علنية فقط.

جارٍ المصادقة

يمكن استخدام مكتبة عميل JavaScript في وضعَين. إذا كنت تكتب أداة، فإنها تستخدم ميزة تسمى الخادم الوكيل OAuth للمصادقة. وإذا تم الوصول إليه من تطبيق JavaScript مستقل، يستخدم نظام مصادقة AuthSub. للحصول على معلومات حول المصادقة، راجع مستند نظرة عامة على مصادقة Google Data APIs. يفترض الجزء المتبقي من هذا القسم أنك على دراية بأساسيات آلية عمل هذا النظام.

قبل استخدام المصادقة مع نموذج الشفرة الموضح في هذا المستند، غيّر عنوان URL للخلاصة من عام إلى خاص:

var feedUrl = "http://www.google.com/calendar/feeds/liz@gmail.com/private/full";

المصادقة في برنامج ويب باستخدام AuthSub

لم يعد نظام التفويض "AuthSub for JavaScript" من Google متاحًا.

وبدلاً من ذلك، نوصي باستخدام OAuth 2.0 للتطبيقات من جهة العميل.

المصادقة في أداة باستخدام خادم وكيل OAuth

في ما يلي نظرة عامة مختصرة على ما يحدث أثناء عملية المصادقة للأداة:

  1. يتم تحميل الأداة للمرة الأولى وتحاول الوصول إلى بيانات المستخدم باستخدام إحدى واجهات برمجة التطبيقات لبيانات Google.
  2. تعذَّرت تلبية الطلب لعدم منح المستخدم إذن الوصول إلى بياناته بعد. يحتوي كائن الاستجابة على عنوان URL (في response.oauthApprovalUrl) لصفحة موافقة OAuth. يجب أن توفر الأداة طريقة لإطلاق نافذة جديدة بعنوان URL هذا.
  3. في صفحة الموافقة، يختار المستخدم منح/رفض الوصول إلى أداتك. في حالة نجاح هذا الإجراء، يتم نقل المستخدم إلى صفحة oauth_callback التي تحددها. للحصول على أفضل تجربة للمستخدم، استخدم http://oauth.gmodules.com/gadgets/oauthcallback.
  4. بعد ذلك، يغلق المستخدم النافذة المنبثقة. للمساعدة في إشعار أداتك بأن المستخدم قد منح الموافقة، قدمنا معالجًا منبثقًا يمكنك استخدامه لاكتشاف إغلاق نافذة الموافقة. وبدلاً من ذلك، يمكن أن تعرض الأداة رابطًا (على سبيل المثال، "أوافق على الدخول") حتى ينقر المستخدم يدويًا بعد إغلاق هذه النافذة.
  5. تحاول أداتك الدخول إلى واجهة برمجة تطبيقات بيانات Google مرة ثانية عن طريق إعادة طلب بيانات المستخدم. تمت هذه المحاولة بنجاح.
  6. تمت مصادقة أداتك ويمكن أن تبدأ في العمل بشكل طبيعي.

في الأداة، أضف عنصر <OAuth> في القسم <ModulePrefs>:

<ModulePrefs>
...
<OAuth>
  <Service name="google">
    <Access url="https://www.google.com/accounts/OAuthGetAccessToken" method="GET" /> 
    <Request url="https://www.google.com/accounts/OAuthGetRequestToken?
                  scope=http://www.blogger.com/feeds/%20http://www.google.com/calendar/feeds/" method="GET" /> 
    <Authorization url="https://www.google.com/accounts/OAuthAuthorizeToken?
                        oauth_callback=http://oauth.gmodules.com/gadgets/oauthcallback" /> 
  </Service>
</OAuth>
...
</ModulePrefs>

في هذا القسم، غيِّر معامِلات طلب البحث التالية:

  • scope

    معلمة مطلوبة في عنوان URL للطلب. ستتمكّن أداتك من الوصول إلى البيانات فقط من scope (العناصر) المستخدمة في هذه المعلمة. في هذا المثال، ستدخل الأداة بيانات Blogger والتقويم الخاصة بك. ويمكن للأداة طلب بيانات لنطاق واحد أو عدة نطاقات (كما هو موضح في هذا المثال).

  • oauth_callback

    معلمة اختيارية في عنوان URL للتفويض. ستتم إعادة توجيه صفحة موافقة OAuth إلى عنوان URL هذا بعد موافقة المستخدم على الوصول إلى بياناته. ويمكنك اختيار ترك هذه المعلمة أو ضبطها على "الصفحة التي تمت الموافقة عليها" أو استخدام http://oauth.gmodules.com/gadgets/oauthcallback إذا كان ذلك مفضلاً. ويقدم الإصدار الأحدث أفضل تجربة للمستخدم عند تثبيت الأداة لأول مرة. توفر هذه الصفحة مقتطف جافا سكريبت الذي يغلق النافذة المنبثقة تلقائيًا.

بعد ذلك، حمّل مكتبة عميل جافا سكريبت في القسم <Content> من الأداة. عدّل الدالة setupMyService() من الأمثلة السابقة لاستدعاء طريقة useOAuth() لكائن الخدمة. يؤدي هذا إلى إخبار الأداة باستخدام خادم وكيل OAuth للمصادقة بدلاً من AuthSub. يجب أن يساعدك النموذج التالي في البدء:

<Content type="html">
<![CDATA[
  ...
  <script src="https://www.google.com/jsapi"></script>
  <script type="text/javascript">
    var myService = null;
    
    function setupMyService() {
      myService = new google.gdata.calendar.CalendarService('exampleCo-exampleApp-1');
      myService.useOAuth('google');
      fetchData();
    }
    
    function initGadget() {
      google.load('gdata', '2.x');
      google.setOnLoadCallback(setupMyService);
    }

    function fetchData() {            
      var callback = function(response) {
        if (response.oauthApprovalUrl) {
        
          // TODO: Display "Sign in" link (response.oauthApprovalUrl contains the URL) 
          
        } else if (response.feed) {
        
          // TODO: show results
          
        } else {
        
          // TODO: handle the error
          
        }
      };

      myService.getEventsFeed('http://www.google.com/calendar/feeds/default/public/full', callback, callback);
    }
    
    gadgets.util.registerOnLoadHandler(initGadget);
  </script>
  ...
]]> 
</Content>

لاحظ أنه تمت إزالة الاتصال بـ google.accounts.user.login(scope). يتعامل الخادم الوكيل مع المصادقة نيابةً عنك.

لمزيد من المعلومات حول كتابة أدوات واجهة برمجة التطبيقات لبيانات Google، بما في ذلك تفاصيل ما يجب أن يحتوي عليه fetchData()، يمكنك الاطلاع على مقالتنا حول إنشاء أداة بيانات Google أو الاطلاع على الوثائق الكاملة لكتابة أدوات OAuth.

إدراج عنصر جديد

لإنشاء حدث تقويم جديد، يمكنك مواصلة التنفيذ من المثال السابق من خلال تعديل نهاية الدالة handleMyFeed() لطلب دالة جديدة:

function handleMyFeed(myResultsFeedRoot) {
  alert("This feed's title is: " + myResultsFeedRoot.feed.getTitle().getText());
  insertIntoMyFeed(myResultsFeedRoot);
}

في الدالة الجديدة، استخدِم دالة الإنشاء CalendarEventEntry أولاً لإنشاء الإدخال الجديد. ثم أدخل الإدخال، لتقديم استدعاء للخدمة لاستدعاءه عند الانتهاء من الإدراج.

function insertIntoMyFeed(feedRoot) {
  var newEntry = new google.gdata.calendar.CalendarEventEntry({
      authors: [{
        name: "Elizabeth Bennet",
        email: "liz@gmail.com"
      }],
      title: {
        type: 'text', 
        text: 'Tennis with Darcy'
      },
      content: {
        type: 'text', 
        text: 'Meet for a quick lesson'
      },
      locations: [{
        rel: "g.event",
        label: "Event location",
        valueString: "Netherfield Park tennis court"
      }],
      times: [{
        startTime: google.gdata.DateTime.fromIso8601("2007-09-23T18:00:00.000Z"),
        endTime: google.gdata.DateTime.fromIso8601("2007-09-23T19:00:00.000Z")
      }]
  });
  feedRoot.feed.insertEntry(newEntry, handleMyInsertedEntry, handleError);
}

لاحظ أن اسم كل خاصية كائن مستخدم في دالة الإنشاء يتطابق مع اسم طريقة دالة setter المستخدمة لتلك الخاصية. (بدلاً من مطابقة اسم حقل JSON المقابل مثلاً).

وتجدر الإشارة أيضًا إلى أنه لا يمكنك تقديم سلاسل التاريخ والوقت ISO 8601 لـ startTime وendTime فقط، بل يجب تشغيل هذه السلاسل من خلال طريقة fromIso8601() أولاً.

تعرض الخدمة نسخة من الإدخال المدرج ككائن entryRoot، وتمرِّر هذا الكائن إلى معاودة الاتصال:

function handleMyInsertedEntry(insertedEntryRoot) {
  alert("Entry inserted. The title is: " + insertedEntryRoot.entry.getTitle().getText());
  alert("The timestamp is: " + insertedEntryRoot.entry.getTimes()[0].startTime);
}

طلب إدخال محدد

لطلب إدخال محدد، عدّل أولاً الدالة handleMyInsertedEntry() لاستدعاء وظيفة جديدة لطلب الإدخال:

function handleMyInsertedEntry(insertedEntryRoot) {
  alert("Entry inserted. The title is: " + insertedEntryRoot.entry.getTitle().getText());
  alert("The timestamp is: " + insertedEntryRoot.entry.getTimes()[0].startTime);
  requestMySpecificEntry(insertedEntryRoot.entry.getSelfLink().getHref());
}

تتيح لك الشفرة التالية طلب الإدخال المحدد الذي أدرجته في المثال السابق.

في سياق سلسلة الأمثلة هذه، لا يكون استرداد هذا الإدخال ضروريًا لأن "تقويم Google" عرض الإدخال المدرج من قبل، ولكن يمكن تطبيق الأسلوب نفسه عندما تعرف عنوان URI لإدخال معيّن.

function requestMySpecificEntry(entryURI) {
  myService.getEventsEntry(entryURI, handleMySpecificEntry, handleError);
}

function handleMySpecificEntry(retrievedEntryRoot) {
  myEntryRoot = retrievedEntryRoot; // Global variable for later use
  alert("This entry's title is: " + retrievedEntryRoot.entry.getTitle().getText());
}

هذا المثال يماثل مثال getEventsFeed()، إلا أننا نستدعي طريقة getEventEntry() للخدمة للحصول على إدخال محدد، ومعرف الموارد المنتظم (URI) مختلف قليلاً - فهو يستخدم "تلقائي" للإشارة إلى التقويم الرئيسي للمستخدم الذي تمت المصادقة عليه، ويوجد رقم تعريف إدخال في نهايته.

كما يلزم أن نتمكن من استخدام الإدخال الذي تم استرداده لاحقًا، لذلك ننسخه إلى متغير عمومي.

البحث في الإدخالات

لإجراء بحث بالنص الكامل، عدِّل أولاً الدالة handleMySpecificEntry() لاستدعاء وظيفة بحث جديدة:

function handleMySpecificEntry(retrievedEntryRoot) {
  myEntryRoot = retrievedEntryRoot; // Global variable for later use
  alert("This entry's title is: " + retrievedEntryRoot.entry.getTitle().getText());
  searchMyFeed();
}

ثم لاسترداد أول تطابق من البحث، استخدم الشفرة التالية:

function searchMyFeed() {
  var myQuery = new google.gdata.calendar.CalendarEventQuery(feedUrl);
  myQuery.setFullTextQuery("Tennis");
  myQuery.setMaxResults(10);
  myService.getEventsFeed(myQuery, handleMyQueryResults, handleError);
}

function handleMyQueryResults(myResultsFeedRoot) {
  if (myResultsFeedRoot.feed.getEntries()[0]) {
    alert("The first search-match entry's title is: " + myResultsFeedRoot.feed.getEntries()[0].getTitle().getText());
  }
  else {
    alert("There are no entries that match the search query.");
  }
}

تحديث عنصر

لتحديث عنصر حالي، أضف أولاً سطرًا إلى نهاية handleMyQueryResults() لاستدعاء وظيفة تحديث جديدة:

  updateMyEntry();

ثم استخدم الرمز التالي. في هذا المثال، نحن بصدد تغيير عنوان الإدخال الذي تم استرداده من قبل (والذي كان مضمنًا في العنصر العمومي المسمى myEntryRoot في مثال سابق) من نصه القديم ("تنس مع دارسي") إلى "اجتماع مهم".

function updateMyEntry() {
  myEntryRoot.entry.getTitle().setText("Important meeting");
  myEntryRoot.entry.updateEntry(handleMyUpdatedEntry, handleError);
}

function handleMyUpdatedEntry(updatedEntryRoot) {
  alert("Entry updated. The new title is: " + updatedEntryRoot.entry.getTitle().getText());
}

وكما هو الحال مع جميع طرق التقويم، تحدد طريقة updateEntry() تلقائيًا معرف الموارد المنتظم (URI) للتعديل الصحيح لاستخدامه في تحديث الإدخال، لذا لا يلزمك تقديم معرف الموارد المنتظم (URI) هذا بشكل صريح.

حذف عنصر

لحذف الإدخال المُعدّل، أضِف أولاً سطرًا إلى handleMyUpdatedEntry():

 deleteMyEntry(updatedEntryRoot);

ثم استخدم الشفرة التالية:

function deleteMyEntry(updatedEntryRoot) {
  updatedEntryRoot.entry.deleteEntry(handleMyDeletedEntry, handleError);
}

function handleMyDeletedEntry() {
  alert("Entry deleted");
}

مرة أخرى، تحدد طريقة deleteEntry() تلقائيًا معرف الموارد المنتظم (URI) الصحيح للتعديل المراد استخدامه في حذف الإدخال.

لاحظ أنه لا يتم عرض أي إدخال. إذا تم استدعاء معاودة الاتصال، فهذا يعني أننا نعرف أن عملية الحذف تمت بنجاح؛ وفي حالة فشل الحذف، يتصل deleteEntry() بـ handleError() بدلاً من استدعاء handleMyDeletedEntry().

استخدام ETags

ملاحظة: لا يمكن استخدام أداة ETags إلا مع الخدمات التي تعمل بالإصدار 2.0 من بروتوكول Google Data.

المقدمة

يقدّم الإصدار 2 من عميل JavaScript لبيانات Google إمكانية استخدام أداة ETags. ETags هي معرّفات تحدد إصدارًا معينًا من إدخال معين، ويعد هذا أمرًا مهمًا في حالتين:

  • إجراء "استرداد مشروط" يطلب فيه أحد العملاء إدخالاً، ويرسل الخادم الإدخال فقط في حالة تغيير الإدخال منذ آخر مرة طلبه العميل.
  • ضمان عدم استبدال أكثر من عميل لتغييرات بعضهم البعض بدون قصد. وتنفذ واجهات برمجة التطبيقات للبيانات إجراء التحديثات وعمليات الحذف إذا حدد العميل علامة ETag قديمة للإدخال.

هناك نوعان من علامات ETags: ضعيفة وقوية. دائمًا ما تبدأ قيمة ETag الضعيفة بـ W/، على سبيل المثال: W/"D08FQn8-eil7ImA9WxZbFEw". ليس هناك ما يضمن تغيير ETags الضعيفة عند تغيير الإدخال، وبالتالي يسمح HTTP باستخدامها للاسترجاع المشروط فقط. تحدّد أداة ETags القوية إصدارًا معيّنًا من إدخال معيّن، ويمكن استخدامها لاسترداد البيانات بشكل شرطي وخلال التعديلات أو عمليات الحذف لتجنّب استبدال تغييرات برامج أخرى. وبسبب هذا التمييز، لن تسمح لك مكتبة العملاء بإرسال علامات ETags الضعيفة مع طلب التعديل أو الحذف.

يمكن العثور على أداة ETags في موقعين في استجابة الخادم:

  • في عنوان HTTP ETag.
  • في الخلاصة/إدخال السمة gd:etag

إذا كانت إحدى الخدمات تدعم الإصدار 2، فسيكون لكل كائن خلاصة وكائن إدخال طريقة getEtag() لاسترداد قيمة ETag.

يدعم عميل JavaScript طريقتين لتضمين ETags مع طلب. العنصر الأول هو كائن opt_params الجديد. تحتوي جميع دوال get/update/insert في الإصدار 2 من مكتبة العميل على معلَمة opt_params جديدة. يُستخدم هذا الكائن لتحديد معلمات اختيارية عند تقديم طلب. في الوقت الحالي، 'etag' هي المعلمة الاختيارية الوحيدة المتاحة (على الرغم من إمكانية تقديم معلمات أخرى في المستقبل). على سبيل المثال، يمكنك إضافة ETag إلى طلب GET على النحو التالي:

var opt_params = {};
opt_params['etag'] = 'ETAG GOES HERE';
service.getFeed(uri, successHandler, errorHandler, opt_params);

يمكنك أيضًا إضافة ETag مباشرةً إلى الخلاصة أو كائن الإدخال من خلال استدعاء طريقة setEtag() في الخلاصة/إدخال الإدخال.

يمكنك معرفة المزيد من المعلومات حول أداة ETags من مرجع بروتوكول GData.

استخدام أداة ETags لاسترداد البيانات

يمكن أن تساعد أداة ETags في تقليل معدل نقل البيانات ووقت التنفيذ عند استرداد البيانات. قد يتم تضمين ETag في طلب GET مع If-None-Match header:

If-None-Match: ETAG GOES HERE

في حال تطابق ETag مع الإصدار الحالي من الخلاصة أو الإدخال، سيستجيب الخادم باستجابة 304 NOT MODIFIED ونص فارغ. وبخلاف ذلك، سيستجيب الخادم باستجابة 200 OK وبيانات الخلاصة أو الإدخال.

يمكنك استخدام ETags في برنامج JavaScript من خلال تضمين معلَمة 'etag' عند تقديم الطلب:

var etag = feed.getEtag(); // Feed loaded from a previous request
var opt_params = {};
opt_params['etag'] = etag;
service.getFeed(feedUrl, successHandler, errorHandler, opt_params);

تعمل عمليات الاسترجاع المشروطة مع كل من ETags القوية والضعيفة. إذا كان ETag متطابقًا، فسيتم استدعاء معالج الخطأ مع الاستجابة 304:

function successHandler(feedRoot) {
  // 200 response
  // Update UI to display updates
}

function errorHandler(errorObj) {
  if (errorObj.cause.getStatus() == 304) {
    // 304 response, do nothing
  }
  // otherwise the response is some other error
}

ألقِ نظرة على نموذج الاسترداد المشروط باستخدام Blogger للاطّلاع على مثال عملي على استخدام ETags في برنامج JavaScript. يفحص هذا النموذج Blogger على فترات زمنية كل 5 ثوانٍ للبحث عن تحديثات لمدونتك. عندما تكون هناك تغييرات، يعمل النموذج على تحديث قائمة بالمشاركات.

استخدام أداة ETags لتعديل البيانات وحذفها

ويضمن استخدام أداة ETags في طلبات التحديث/الحذف ألا يستبدل العديد من العملاء تغييرات بعضهم البعض بدون قصد. في هذه الحالة، يتم تضمين ETag مع عنوان If-Match:

If-Match: ETAG GOES HERE

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

في بعض الحالات، قد تحتاج إلى فرض تنفيذ التغييرات، بغض النظر عن أي تغييرات أخرى على الإدخال. ويمكنك إجراء ذلك من خلال تمرير * إلى العنوان If-Match:

If-Match: *

ضع في اعتبارك أن هذا سيؤدي إلى إلغاء التغييرات التي أجراها العملاء الآخرون، لذا استخدم هذا بعناية.

يمكنك فقط تحديث/حذف إدخال باستخدام ETag قوي. سيؤدي تحديد قيمة ETag ضعيفة إلى حدوث خطأ. للحماية من هذه الحالة، لن يعيّن برنامج JavaScript علامات ETags ضعيفة على طلبات التحديث والحذف.

يتم استخدام ETags بالطريقة نفسها التي يتم بها استخدام عمليات الاسترجاع الشرطي:

function updateData(entry, service) {
  var etag = entry.getEtag();
  var opt_params = {};
  opt_params['etag'] = etag; // Or use '*' to force an update.
  service.updateEntry(successHandler, errorHandler, opt_params);
}

function successHandler(response) {
  // Successful update
}

function errorHandler(errorObj) {
  // ERROR - Update failed. Could be due to an ETag mismatch, but check the
  // error message to make sure. An ETag error will be in the format:
  // Mismatch: etags = ["Qnc-fTVSLyp7ImA9WxJbFEsDRAw."], version = [1249675665358000]
}

عند إجراء التحديثات، يمكن تحديد ETag في مكانين:

  1. في الإدخال نفسه، باستخدام الطريقتين getEtag() وsetEtag().
  2. في العنوان، باستخدام الكائن opt_params (كما هو موضّح أعلاه).

ستحتوي إحدى الإدخالات التي تم تحميلها من طلب GET سابق على مجموعة حقول ETag. لذلك، يعد تحديد علامة ETag نفسها في الكائن opt_params أمرًا مكررًا. في حالة تحديد ETag في كل من نص الإدخال وopt_params، تكون الأولوية لـ ETag في opt_params. وقد يؤدي هذا إلى إرباك بعض الشيء، لذلك إذا كنت تواجه مشاكل في التحديثات الشرطية، احرص على التحقق من ETag في كل من الإدخال والكائن opt_params.

ولتسهيل الأمر، يجب أن تكون للصفوف في google.gdata.Entry طريقة updateEntry() وdeleteEntry() خاصة بها. إذا كانت فئة المشاركة تحتوي على علامة ETag، لن تحتاج إلى إضافتها إلى الطلب، لأن مكتبة العملاء ستتولى ذلك تلقائيًا. مثلاً:

// entry was loaded from a previous request.  No need to specify
// an ETag in opt_params here, it is added automatically.
entry.deleteEntry(successHandler, errorHandler);

ويمنحك هذا فائدة من أداة ETags بدون القلق بشأن ضبطها بشكل صحيح. ولكن إذا كنت تريد فرض التحديث باستخدام '*'، عليك دائمًا تضمين الكائن opt_params مع 'etag' = '*'.

يمكنك الاطلاع على التحديثات الشرطية في العمل من خلال التحديثات الشرطية في جهات الاتصال. ينشئ النموذج أولاً مجموعة جهات اتصال تجريبية يتم فيها إنشاء جميع البيانات التي تستخدمها هذه العينة. لا تتردد في حذف مجموعة جهات الاتصال هذه عند الانتهاء من استخدام النموذج. ثم يحمّل النموذج إطاري iframe مع المحتوى من مجموعة جهات الاتصال. يمكنك إجراء التحديثات في إطار iframe واحد والاطلاع على مدى تأثيره في التحديثات في إطار iframe الآخر. انتقل إلى النموذج للحصول على مزيد من التفاصيل حول كيفية استخدامه.

نماذج

مَراجع

للحصول على معلومات مرجعية حول الفئات والطرق المتاحة من خلال مكتبة العميل، اطلع على مرجع واجهة برمجة تطبيقات مكتبة عميل جافا سكريبت (بتنسيق JSdoc).

الرجوع إلى الأعلى