معاينة الروابط

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

على سبيل المثال، تخيَّل مساحة في Google Chat تتضمن جميع موظّفي خدمة العملاء في الشركة، بالإضافة إلى تطبيق Chat المسمى Case-y. يشارك موظّفو الدعم بشكل متكرر روابط تؤدي إلى طلبات خدمة العملاء في "مساحة Chat"، وفي كل مرة يجرون فيها هذه العملية، على زملائهم فتح رابط الطلب للاطّلاع على تفاصيل، مثل المُسنَد إليه والحالة والموضوع. وبالمثل، إذا أراد أحد الأشخاص الحصول على ملكية إحدى الطلبات أو تغيير حالتها، فعليه فتح الرابط.

تتيح معاينة الروابط لتطبيق Chat، Case-y، المتوفّر في المساحة، إرفاق بطاقة توضّح المسؤول عن الإسناد والحالة والموضوع عندما يشارك أحد المستخدمين رابط طلب. من خلال الأزرار الموجودة على البطاقة، يمكن لموظّفي الدعم الاستحواذ على ملكية الطلب وتغيير الحالة مباشرةً من بث المحادثة.

عندما يضيف مستخدم رابطًا إلى رسالته، تظهر شريحة تتيح له معرفة أنّ تطبيق Chat قد يعاين الرابط.

شريحة تشير إلى أنّ تطبيق Chat قد يعاين رابطًا.

بعد إرسال الرسالة، يتم إرسال الرابط إلى تطبيق Chat الذي ينشئ البطاقة في رسالة المستخدم ويرفقها.

يعاين تطبيق Chat رابطًا من خلال إرفاق بطاقة بالرسالة

إلى جانب الرابط، توفر البطاقة معلومات إضافية حول الرابط، بما في ذلك العناصر التفاعلية مثل الأزرار. يمكن لتطبيق Chat تعديل البطاقة المرفقة استجابةً لتفاعلات المستخدمين، مثل النقرات على الأزرار.

إذا كان المستخدم لا يريد أن يعاين تطبيق Chat الرابط من خلال إرفاق بطاقة برسالته، يمكنه منع المعاينة من خلال النقر على في شريحة المعاينة. يمكن للمستخدمين إزالة البطاقة المرفقة في أي وقت بالنقر على إزالة المعاينة.

يمكنك تسجيل روابط محدّدة، مثل example.com وsupport.example.com وsupport.example.com/cases/، كأنماط عناوين URL على صفحة ضبط تطبيق Chat في Google Cloud Console لكي يتمكّن تطبيق Chat من معاينتها.

قائمة ضبط معاينات الروابط

  1. افتح Google Cloud Console.
  2. بجانب Google Cloud، انقر على السهم المتّجه للأسفل وافتح مشروع تطبيق Chat.
  3. في حقل البحث، اكتب Google Chat API وانقر على Google Chat API.
  4. انقر على إدارة > الضبط.
  5. ضمن "معاينات الروابط"، أضِف نمط عنوان URL أو عدِّله.
    1. لضبط معاينات الروابط لنمط عنوان URL جديد، انقر على إضافة نمط عنوان URL.
    2. لتعديل إعدادات نمط عنوان URL حالي، انقر على السهم المتّجه للأسفل .
  6. في حقل نمط المضيف، أدخِل نطاق نمط عنوان URL. سيعاين تطبيق Chat الروابط المؤدية إلى هذا النطاق.

    للحصول على روابط معاينة التطبيق على Chat لنطاق فرعي محدّد، مثل subdomain.example.com، يجب تضمين النطاق الفرعي.

    للحصول على روابط معاينة تطبيق Chat للنطاق بأكمله، حدِّد حرف بدل مع علامة النجمة (*) كنطاق فرعي. على سبيل المثال، تتطابق السمة *.example.com مع subdomain.example.com وany.number.of.subdomains.example.com.

  7. في حقل بادئة المسار، أدخِل مسارًا لإلحاقه بنطاق نمط المضيف.

    لمطابقة جميع عناوين URL في نطاق نمط المضيف، اترك بادئة المسار فارغة.

    مثلاً، إذا كان نمط المضيف هو support.example.com، أدخِل cases/ لمطابقة عناوين URL للتجارب المستضافة في support.example.com/cases/.

  8. انقر على تم.

  9. انقر على حفظ.

والآن، عندما يضيف مستخدم رابطًا يتطابق مع نمط عنوان URL لمعاينة رابط مع رسالة في "مساحة Chat" تتضمّن تطبيق Chat، يعاين تطبيقك الرابط.

بعد ضبط معاينة الرابط لرابط معيّن، يمكن لتطبيق Chat التعرّف على الرابط ومعاينته من خلال إرفاق المزيد من المعلومات إليه.

داخل مساحات Chat التي تتضمّن تطبيق Chat، عندما تحتوي رسالة أحد المستخدمين على رابط يتطابق مع نمط عنوان URL لمعاينة الرابط، يتلقّى تطبيق Chat حدث تفاعل MESSAGE. تحتوي حمولة بيانات JSON لحدث التفاعل على الحقل matchedUrl:

JSON

"message": {

  . . . // other message attributes redacted

  "matchedUrl": {
     "url": "https://support.example.com/cases/case123"
   },

  . . . // other message attributes redacted

}

من خلال التحقّق من توفُّر الحقل matchedUrl في حمولة الحدث MESSAGE، يمكن لتطبيق Chat إضافة معلومات إلى الرسالة باستخدام الرابط الذي تمت معاينته. ويمكن لتطبيق Chat إما الرد برسالة نصية بسيطة أو إرفاق بطاقة.

الرد برسالة نصية

للحصول على ردود بسيطة، يمكن لتطبيق Chat معاينة رابط عن طريق الرد باستخدام رسالة نصية بسيطة على رابط. هذا المثال يرفق رسالة تكرر عنوان URL للرابط الذي يتطابق مع نمط عنوان URL لمعاينة الرابط.

Node.js

node/preview-link/simple-text-message.js
/**
 * Responds to messages that have links whose URLs match URL patterns
 * configured for link previewing.
 *
 * @param {Object} req Request sent from Google Chat.
 * @param {Object} res Response to send back.
 */
exports.onMessage = (req, res) => {
  if (req.method === 'GET' || !req.body.message) {
    return res.send(
      'Hello! This function is meant to be used in a Google Chat Space.');
  }

  // Checks for the presence of event.message.matchedUrl and responds with a
  // text message if present
  if (req.body.message.matchedUrl) {
    return res.json({
      'text': 'req.body.message.matchedUrl.url: ' +
        req.body.message.matchedUrl.url,
    });
  }

  // If the Chat app doesn’t detect a link preview URL pattern, it says so.
  return res.json({'text': 'No matchedUrl detected.'});
};

برمجة تطبيقات

apps-script/preview-link/simple-text-message.gs
/**
 * Responds to messages that have links whose URLs match URL patterns
 * configured for link previewing.
 *
 * @param {Object} event The event object from Chat API.
 *
 * @return {Object} Response from the Chat app attached to the message with
 * the previewed link.
 */
function onMessage(event) {
  // Checks for the presence of event.message.matchedUrl and responds with a
  // text message if present
  if (event.message.matchedUrl) {
    return {
      'text': 'event.message.matchedUrl.url: ' + event.message.matchedUrl.url,
    };
  }

  // If the Chat app doesn’t detect a link preview URL pattern, it says so.
  return {'text': 'No matchedUrl detected.'};
}

إرفاق بطاقة

لإرفاق بطاقة برابط تمت معاينته، يُرجى عرض ActionResponse من النوع UPDATE_USER_MESSAGE_CARDS. هذا المثال يرفق بطاقة بسيطة.

يعاين تطبيق Chat رابطًا من خلال إرفاق بطاقة بالرسالة

Node.js

node/preview-link/attach-card.js
/**
 * Responds to messages that have links whose URLs match URL patterns
 * configured for link previewing.
 *
 * @param {Object} req Request sent from Google Chat.
 * @param {Object} res Response to send back.
 */
exports.onMessage = (req, res) => {
  if (req.method === 'GET' || !req.body.message) {
    return res.send(
      'Hello! This function is meant to be used in a Google Chat Space.');
  }

  // Checks for the presence of event.message.matchedUrl and attaches a card
  // if present
  if (req.body.message.matchedUrl) {
    return res.json({
      'actionResponse': {'type': 'UPDATE_USER_MESSAGE_CARDS'},
      'cardsV2': [
        {
          'cardId': 'attachCard',
          'card': {
            'header': {
              'title': 'Example Customer Service Case',
              'subtitle': 'Case basics',
            },
            'sections': [
              {
                'widgets': [
                  {'keyValue': {'topLabel': 'Case ID', 'content': 'case123'}},
                  {'keyValue': {'topLabel': 'Assignee', 'content': 'Charlie'}},
                  {'keyValue': {'topLabel': 'Status', 'content': 'Open'}},
                  {
                    'keyValue': {
                      'topLabel': 'Subject', 'content': 'It won"t turn on...',
                    }
                  },
                ],
              },
              {
                'widgets': [
                  {
                    'buttons': [
                      {
                        'textButton': {
                          'text': 'OPEN CASE',
                          'onClick': {
                            'openLink': {
                              'url': 'https://support.example.com/orders/case123',
                            },
                          },
                        },
                      },
                      {
                        'textButton': {
                          'text': 'RESOLVE CASE',
                          'onClick': {
                            'openLink': {
                              'url': 'https://support.example.com/orders/case123?resolved=y',
                            },
                          },
                        },
                      },
                      {
                        'textButton': {
                          'text': 'ASSIGN TO ME',
                          'onClick': {
                            'action': {
                              'actionMethodName': 'assign',
                            },
                          },
                        },
                      },
                    ],
                  },
                ],
              },
            ],
          },
        },
      ],
    });
  }

  // If the Chat app doesn’t detect a link preview URL pattern, it says so.
  return res.json({'text': 'No matchedUrl detected.'});
};

برمجة تطبيقات

apps-script/preview-link/attach-card.gs
/**
 * Responds to messages that have links whose URLs match URL patterns
 * configured for link previewing.
 *
 * @param {Object} event The event object from Chat API.
 * @return {Object} Response from the Chat app attached to the message with
 * the previewed link.
 */
function onMessage(event) {
  // Checks for the presence of event.message.matchedUrl and attaches a card
  // if present
  if (event.message.matchedUrl) {
    return {
      'actionResponse': {
        'type': 'UPDATE_USER_MESSAGE_CARDS',
      },
      'cardsV2': [{
        'cardId': 'attachCard',
        'card': {
          'header': {
            'title': 'Example Customer Service Case',
            'subtitle': 'Case basics',
          },
          'sections': [{
            'widgets': [
              {'keyValue': {'topLabel': 'Case ID', 'content': 'case123'}},
              {'keyValue': {'topLabel': 'Assignee', 'content': 'Charlie'}},
              {'keyValue': {'topLabel': 'Status', 'content': 'Open'}},
              {
                'keyValue': {
                  'topLabel': 'Subject', 'content': 'It won\'t turn on...',
                },
              },
            ],
          },
          {
            'widgets': [{
              'buttons': [
                {
                  'textButton': {
                    'text': 'OPEN CASE',
                    'onClick': {
                      'openLink': {
                        'url': 'https://support.example.com/orders/case123',
                      },
                    },
                  },
                },
                {
                  'textButton': {
                    'text': 'RESOLVE CASE',
                    'onClick': {
                      'openLink': {
                        'url': 'https://support.example.com/orders/case123?resolved=y',
                      },
                    },
                  },
                },
                {
                  'textButton': {
                    'text': 'ASSIGN TO ME',
                    'onClick': {'action': {'actionMethodName': 'assign'}},
                  },
                },
              ],
            }],
          }],
        },
      }],
    };
  }

  // If the Chat app doesn’t detect a link preview URL pattern, it says so.
  return {'text': 'No matchedUrl detected.'};
}

تعديل بطاقة

لتعديل البطاقة المرفقة برابط تمّت معاينته، يجب عرض ActionResponse من النوع UPDATE_USER_MESSAGE_CARDS. يمكن لتطبيقات Chat تعديل البطاقات التي تعاين الروابط فقط كردّ على حدث تفاعل مع تطبيق Chat. لا يمكن لتطبيقات Chat تحديث هذه البطاقات من خلال إرسال طلب إلى Chat API بشكل غير متزامن.

لا تتيح معاينة الرابط عرض ActionResponse من النوع UPDATE_MESSAGE. بما أنّ تطبيق "UPDATE_MESSAGE" يعدّل الرسالة بالكامل بدلاً من البطاقة فقط، لا يعمل إلا إذا كان تطبيق Chat قد أنشأ الرسالة الأصلية. تؤدي ميزة "معاينة الرابط" إلى إرفاق بطاقة برسالة أنشأها المستخدم، لذلك لا يملك تطبيق Chat الإذن بتعديلها.

لضمان تعديل إحدى الوظائف لكل من البطاقات التي أنشأها المستخدمون أو التي أنشأها التطبيق في ساحة مشاركات Chat، يمكنك ضبط ActionResponse ديناميكيًا استنادًا إلى ما إذا كان التطبيق في Chat أو المستخدم هو من أنشأ الرسالة.

  • إذا أنشأ مستخدم الرسالة، اضبط ActionResponse على UPDATE_USER_MESSAGE_CARDS.
  • إذا أنشأ تطبيق في Chat الرسالة، اضبط ActionResponse على UPDATE_MESSAGE.

تتوفّر طريقتان لتنفيذ ذلك: تحديد actionMethodName مخصَّصة والتحقّق منها كجزء من السمة onclick في البطاقة المرفقة (التي تحدِّد الرسالة على أنّها من إنشاء المستخدم) أو التأكّد مما إذا كانت الرسالة من إنشاء المستخدم أم لا.

الخيار 1: البحث عن actionMethodName

لاستخدام actionMethodName للتعامل بشكلٍ سليم مع أحداث تفاعل CARD_CLICKED على البطاقات التي تمت معاينتها، يمكنك ضبط سمة actionMethodName مخصّصة كجزء من السمة onclick للبطاقة المرفقة:

JSON

. . . // Preview card details
{
  "textButton": {
    "text": "ASSIGN TO ME",
    "onClick": {

      // actionMethodName identifies the button to help determine the
      // appropriate ActionResponse.
      "action": {
        "actionMethodName": "assign",
      }
    }
  }
}
. . . // Preview card details

من خلال تحديد "actionMethodName": "assign" للزر كجزء من معاينة الرابط، يمكن عرض ActionResponse الصحيح ديناميكيًا من خلال البحث عن actionMethodName مطابق:

Node.js

node/preview-link/update-card.js
/**
 * Responds to messages that have links whose URLs match URL patterns
 * configured for link previewing.
 *
 * @param {Object} req Request sent from Google Chat.
 * @param {Object} res Response to send back.
 */
exports.onMessage = (req, res) => {
  if (req.method === 'GET' || !req.body.message) {
    return res.send(
      'Hello! This function is meant to be used in a Google Chat Space.');
  }

  // Respond to button clicks on attached cards
  if (req.body.type === 'CARD_CLICKED') {
    // Checks for the presence of "actionMethodName": "assign" and sets
    // actionResponse.type to "UPDATE_USER"MESSAGE_CARDS" if present or
    // "UPDATE_MESSAGE" if absent.
    const actionResponseType = req.body.action.actionMethodName === 'assign' ?
      'UPDATE_USER_MESSAGE_CARDS' :
      'UPDATE_MESSAGE';

    if (req.body.action.actionMethodName === 'assign') {
      return res.json({
        'actionResponse': {

          // Dynamically returns the correct actionResponse type.
          'type': actionResponseType,
        },

        // Preview card details
        'cardsV2': [{}],
      });
    }
  }
};

برمجة تطبيقات

apps-script/preview-link/update-card.gs
/**
 * Updates a card that was attached to a message with a previewed link.
 *
 * @param {Object} event The event object from Chat API.
 * @return {Object} Response from the Chat app. Either a new card attached to
 * the message with the previewed link, or an update to an existing card.
 */
function onCardClick(event) {
  // Checks for the presence of "actionMethodName": "assign" and sets
  // actionResponse.type to "UPDATE_USER"MESSAGE_CARDS" if present or
  // "UPDATE_MESSAGE" if absent.
  const actionResponseType = event.action.actionMethodName === 'assign' ?
    'UPDATE_USER_MESSAGE_CARDS' :
    'UPDATE_MESSAGE';

  if (event.action.actionMethodName === 'assign') {
    return assignCase(actionResponseType);
  }
}

/**
 * Updates a card to say that "You" are the assignee after clicking the Assign
 * to Me button.
 *
 * @param {String} actionResponseType Which actionResponse the Chat app should
 * use to update the attached card based on who created the message.
 * @return {Object} Response from the Chat app. Updates the card attached to
 * the message with the previewed link.
 */
function assignCase(actionResponseType) {
  return {
    'actionResponse': {

      // Dynamically returns the correct actionResponse type.
      'type': actionResponseType,
    },
    // Preview card details
    'cardsV2': [{}],
  };
}

الخيار 2: التحقُّق من نوع المُرسِل

تحقَّق لمعرفة ما إذا كان message.sender.type HUMAN أو BOT. إذا كانت السمة HUMAN، يجب ضبط ActionResponse على UPDATE_USER_MESSAGE_CARDS، أو ضبط ActionResponse على UPDATE_MESSAGE. يُرجى اتّباع الخطوات التالية:

Node.js

node/preview-link/sender-type.js
/**
 * Responds to messages that have links whose URLs match URL patterns
 * configured for link previewing.
 *
 * @param {Object} req Request sent from Google Chat.
 * @param {Object} res Response to send back.
 */
exports.onMessage = (req, res) => {
  if (req.method === 'GET' || !req.body.message) {
    return res.send(
      'Hello! This function is meant to be used in a Google Chat Space.');
  }

  // Respond to button clicks on attached cards
  if (req.body.type === 'CARD_CLICKED') {
    // Checks whether the message event originated from a human or a Chat app
    // and sets actionResponse.type to "UPDATE_USER_MESSAGE_CARDS if human or
    // "UPDATE_MESSAGE" if Chat app.
    const actionResponseType = req.body.action.actionMethodName === 'HUMAN' ?
      'UPDATE_USER_MESSAGE_CARDS' :
      'UPDATE_MESSAGE';

    return res.json({
      'actionResponse': {

        // Dynamically returns the correct actionResponse type.
        'type': actionResponseType,
      },

      // Preview card details
      'cardsV2': [{}],
    });
  }
};

برمجة تطبيقات

apps-script/preview-link/sender-type.gs
/**
 * Updates a card that was attached to a message with a previewed link.
 *
 * @param {Object} event The event object from Chat API.
 * @return {Object} Response from the Chat app. Either a new card attached to
 * the message with the previewed link, or an update to an existing card.
 */
function onCardClick(event) {
  // Checks whether the message event originated from a human or a Chat app
  // and sets actionResponse.type to "UPDATE_USER_MESSAGE_CARDS if human or
  // "UPDATE_MESSAGE" if Chat app.
  const actionResponseType = event.message.sender.type === 'HUMAN' ?
    'UPDATE_USER_MESSAGE_CARDS' :
    'UPDATE_MESSAGE';

  return assignCase(actionResponseType);
}

/**
 * Updates a card to say that "You" are the assignee after clicking the Assign
 * to Me button.
 *
 * @param {String} actionResponseType Which actionResponse the Chat app should
 * use to update the attached card based on who created the message.
 * @return {Object} Response from the Chat app. Updates the card attached to
 * the message with the previewed link.
 */
function assignCase(actionResponseType) {
  return {
    'actionResponse': {

      // Dynamically returns the correct actionResponse type.
      'type': actionResponseType,
    },
    // Preview card details
    'cardsV2': [{}],
  };
}

يكون السبب المعتاد لتعديل البطاقة هو الاستجابة للنقر على زر. تذكَّر الزر تعيين إليّ من القسم السابق، إرفاق بطاقة. يؤدّي المثال الكامل التالي إلى تعديل البطاقة بحيث تشير إلى أنّه قد تمّ تخصيصها لـ "أنت" بعد أن ينقر المستخدِم على تعيين لي. يعمل المثال على ضبط ActionResponse ديناميكيًا من خلال التحقّق من نوع المُرسِل.

مثال كامل: حالة تطبيق Chat لخدمة العملاء

في ما يلي الرمز الكامل لتطبيق Case-y في Chat الذي يعاين روابط إلى الطلبات التي تمت مشاركتها في مساحة Chat يتعاون فيها موظّفو خدمة العملاء.

Node.js

node/preview-link/preview-link.js
/**
 * Responds to messages that have links whose URLs match URL patterns
 * configured for link previewing.
 *
 * @param {Object} req Request sent from Google Chat.
 * @param {Object} res Response to send back.
 */
exports.onMessage = (req, res) => {
  if (req.method === 'GET' || !req.body.message) {
    return res.send(
      'Hello! This function is meant to be used in a Google Chat Space.');
  }

  // Respond to button clicks on attached cards
  if (req.body.type === 'CARD_CLICKED') {
    // Checks whether the message event originated from a human or a Chat app
    // and sets actionResponse.type to "UPDATE_USER_MESSAGE_CARDS if human or
    // "UPDATE_MESSAGE" if Chat app.
    const actionResponseType = req.body.action.actionMethodName === 'HUMAN' ?
      'UPDATE_USER_MESSAGE_CARDS' :
      'UPDATE_MESSAGE';

    if (req.body.action.actionMethodName === 'assign') {
      return res.json(createMessage(actionResponseType, 'You'));
    }
  }

  // Checks for the presence of event.message.matchedUrl and attaches a card
  // if present
  if (req.body.message.matchedUrl) {
    return res.json(createMessage());
  }

  // If the Chat app doesn’t detect a link preview URL pattern, it says so.
  return res.json({'text': 'No matchedUrl detected.'});
};

/**
 * Message to create a card with the correct response type and assignee.
 *
 * @param {string} actionResponseType
 * @param {string} assignee
 * @return {Object} a card with URL preview
 */
function createMessage(
  actionResponseType = 'UPDATE_USER_MESSAGE_CARDS',
  assignee = 'Charlie'
) {
  return {
    'actionResponse': {'type': actionResponseType},
    'cardsV2': [
      {
        'cardId': 'previewLink',
        'card': {
          'header': {
            'title': 'Example Customer Service Case',
            'subtitle': 'Case basics',
          },
          'sections': [
            {
              'widgets': [
                {'keyValue': {'topLabel': 'Case ID', 'content': 'case123'}},
                {'keyValue': {'topLabel': 'Assignee', 'content': assignee}},
                {'keyValue': {'topLabel': 'Status', 'content': 'Open'}},
                {
                  'keyValue': {
                    'topLabel': 'Subject', 'content': 'It won"t turn on...',
                  },
                },
              ],
            },
            {
              'widgets': [
                {
                  'buttons': [
                    {
                      'textButton': {
                        'text': 'OPEN CASE',
                        'onClick': {
                          'openLink': {
                            'url': 'https://support.example.com/orders/case123',
                          },
                        },
                      },
                    },
                    {
                      'textButton': {
                        'text': 'RESOLVE CASE',
                        'onClick': {
                          'openLink': {
                            'url': 'https://support.example.com/orders/case123?resolved=y',
                          },
                        },
                      },
                    },
                    {
                      'textButton': {
                        'text': 'ASSIGN TO ME',
                        'onClick': {
                          'action': {
                            'actionMethodName': 'assign',
                          },
                        },
                      },
                    },
                  ],
                },
              ],
            },
          ],
        }
      },
    ],
  };
}

برمجة تطبيقات

apps-script/preview-link/preview-link.gs
/**
 * Responds to messages that have links whose URLs match URL patterns
 * configured for link previews.
 *
 * @param {Object} event The event object from Chat API.
 * @return {Object} Response from the Chat app attached to the message with
 * the previewed link.
 */
function onMessage(event) {
  // Checks for the presence of event.message.matchedUrl and attaches a card
  // if present
  if (event.message.matchedUrl) {
    return {
      'actionResponse': {
        'type': 'UPDATE_USER_MESSAGE_CARDS',
      },
      'cardsV2': [{
        'cardId': 'previewLink',
        'card': {
          'header': {
            'title': 'Example Customer Service Case',
            'subtitle': 'Case basics',
          },
          'sections': [{
            'widgets': [
              {'keyValue': {'topLabel': 'Case ID', 'content': 'case123'}},
              {'keyValue': {'topLabel': 'Assignee', 'content': 'Charlie'}},
              {'keyValue': {'topLabel': 'Status', 'content': 'Open'}},
              {
                'keyValue': {
                  'topLabel': 'Subject', 'content': 'It won\'t turn on...',
                }
              },
            ],
          },
          {
            'widgets': [{
              'buttons': [
                {
                  'textButton': {
                    'text': 'OPEN CASE',
                    'onClick': {
                      'openLink': {
                        'url': 'https://support.example.com/orders/case123',
                      },
                    },
                  },
                },
                {
                  'textButton': {
                    'text': 'RESOLVE CASE',
                    'onClick': {
                      'openLink': {
                        'url': 'https://support.example.com/orders/case123?resolved=y',
                      },
                    },
                  },
                },
                {
                  'textButton': {
                    'text': 'ASSIGN TO ME',
                    'onClick': {'action': {'actionMethodName': 'assign'}}
                  },
                },
              ],
            }],
          }],
        },
      }],
    };
  }

  // If the Chat app doesn’t detect a link preview URL pattern, it says so.
  return {'text': 'No matchedUrl detected.'};
}

/**
 * Updates a card that was attached to a message with a previewed link.
 *
 * @param {Object} event The event object from Chat API.
 * @return {Object} Response from the Chat app. Either a new card attached to
 * the message with the previewed link, or an update to an existing card.
 */
function onCardClick(event) {
  // Checks whether the message event originated from a human or a Chat app
  // and sets actionResponse to "UPDATE_USER_MESSAGE_CARDS if human or
  // "UPDATE_MESSAGE" if Chat app.
  const actionResponseType = event.message.sender.type === 'HUMAN' ?
    'UPDATE_USER_MESSAGE_CARDS' :
    'UPDATE_MESSAGE';

  // To respond to the correct button, checks the button's actionMethodName.
  if (event.action.actionMethodName === 'assign') {
    return assignCase(actionResponseType);
  }
}

/**
 * Updates a card to say that "You" are the assignee after clicking the Assign
 * to Me button.
 *
 * @param {String} actionResponseType Which actionResponse the Chat app should
 * use to update the attached card based on who created the message.
 * @return {Object} Response from the Chat app. Updates the card attached to
 * the message with the previewed link.
 */
function assignCase(actionResponseType) {
  return {
    'actionResponse': {

      // Dynamically returns the correct actionResponse type.
      'type': actionResponseType,
    },
    'cardsV2': [{
      'cardId': 'assignCase',
      'card': {
        'header': {
          'title': 'Example Customer Service Case',
          'subtitle': 'Case basics',
        },
        'sections': [{
          'widgets': [
            {'keyValue': {'topLabel': 'Case ID', 'content': 'case123'}},
            {'keyValue': {'topLabel': 'Assignee', 'content': 'You'}},
            {'keyValue': {'topLabel': 'Status', 'content': 'Open'}},
            {
              'keyValue': {
                'topLabel': 'Subject', 'content': 'It won\'t turn on...',
              }
            },
          ],
        },
        {
          'widgets': [{
            'buttons': [
              {
                'textButton': {
                  'text': 'OPEN CASE',
                  'onClick': {
                    'openLink': {
                      'url': 'https://support.example.com/orders/case123',
                    },
                  },
                },
              },
              {
                'textButton': {
                  'text': 'RESOLVE CASE',
                  'onClick': {
                    'openLink': {
                      'url': 'https://support.example.com/orders/case123?resolved=y',
                    },
                  },
                },
              },
              {
                'textButton': {
                  'text': 'ASSIGN TO ME',
                  'onClick': {'action': {'actionMethodName': 'assign'}},
                },
              },
            ],
          }],
        }],
      },
    }],
  };
}

الحدود والاعتبارات

أثناء ضبط معاينات الروابط لتطبيق Chat، يُرجى مراعاة الحدود والاعتبارات التالية:

  • يتيح كل تطبيق في Chat معاينات الروابط لما يصل إلى 5 أنماط لعناوين URL.
  • تعاين التطبيقات في Chat رابطًا واحدًا لكل رسالة. في حال توفُّر عدة روابط قابلة للمعاينة في رسالة واحدة، تتم معاينة الرابط الأول فقط القابل للمعاينة.
  • لا تعاين تطبيقات Chat سوى الروابط التي تبدأ بالبادئة https://، وبالتالي لا تتم معاينات https://support.example.com/cases/، إلا أنّ support.example.com/cases/ لا تفعل ذلك.
  • يتم إرسال عنوان URL للرابط فقط إلى تطبيق Chat من خلال معاينات الروابط، ما لم تتضمّن الرسالة معلومات أخرى يتم إرسالها إلى تطبيق Chat، مثل الأمر الشرطة المائلة.
  • يمكن استخدام ActionResponse من النوع UPDATE_USER_MESSAGE_CARDS فقط في البطاقات المرفقة بالروابط التي تمت معاينتها، وذلك استجابةً لحدث تفاعل مع تطبيق على Chat فقط. لا تتيح معاينات الروابط استخدام UPDATE_MESSAGE أو الطلبات غير المتزامنة لتعديل البطاقات المرفقة برابط تمت معاينته من خلال Chat API. لمزيد من المعلومات، يمكنك الاطّلاع على تعديل بطاقة.

أثناء تنفيذ معاينات الروابط، قد تحتاج إلى تصحيح الأخطاء في تطبيق Chat من خلال قراءة سجلّات التطبيق. لقراءة السجلات، انتقِل إلى مستكشف السجلات على وحدة تحكُّم Google Cloud.