使用 Google 助理和 Cloud Firestore 的拼字練習遊戲

1. 總覽

透過 Google 助理開發人員平台,您可以建立可擴充 Google 助理 (虛擬個人助理) 功能的軟體,支援超過 10 億部裝置,包括智慧音箱、手機、汽車、電視和耳機等。使用者可以透過對話的方式與 Google 助理互動,例如購買食品雜貨或預約叫車。開發人員可以使用 Google 助理開發人員平台,輕鬆建立及管理使用者和第三方執行服務之間的順暢有效對話體驗。

本程式碼研究室說明使用 Google 助理、Cloud Functions 和 Cloud Firestore 進行開發的中級概念。在本程式碼研究室中,您將建構名為「拼字檢查」的遊戲也就是引導使用者拼法的字詞

建構項目

在本程式碼研究室中,您將建構具有下列功能的精密遊戲:

  • 接收使用者的拼字回覆,並根據值修改對話提示
  • 在回覆中提供與拼字相關的提示,例如字詞定義或重複字詞
  • 建立遊戲迴圈,讓使用者可在拼寫字詞後再次與 Google 助理互動

開始建構前,你可以在支援 Google 助理的裝置上說出「Ok Google,跟拼字練習交談」,與即時動作互動。此動作為回訪者執行此動作的預設路徑,看起來會像這樣:

完成本程式碼研究室後,您完成的動作將具有以下對話流程:

2e9f94dc0ceafc96.png

課程內容

  • 如何與 Cloud Firestore 互動
  • 如何使用運算單元向使用者收集資料
  • 如何處理使用者的輸入內容並傳回回應
  • 如何使用條件在場景中新增邏輯
  • 如何新增遊戲迴圈

軟硬體需求

使用本程式碼研究室的必備條件包括:

  • 使用網路瀏覽器,例如 Google Chrome
  • 用於寫入 Cloud Functions 的 IDE。
  • 付款方式。本程式碼研究室會使用 Cloud Functions for Firebase,因此您的專案必須採用 Firebase Blaze 定價方案 ( 瞭解詳情)。
  • 執行殼層指令的終端機
  • Node.js 10 或以上版本

2. 取得函式程式碼

從指令列複製 GitHub 存放區

$ git clone https://github.com/FirebaseExtended/codelab-actions-firestore

3. 建立 Firebase 專案並設定應用程式

建立 Firebase 專案

  1. 登入 Firebase
  2. 在 Firebase 控制台中,按一下「新增專案」 (或「建立專案」),然後將 Firebase 專案命名為 Spelling-Practice

66ae8d1894f4477.png

  1. 點選專案建立選項。如果系統顯示提示,請接受 Firebase 條款。略過設定 Google Analytics,因為這個應用程式不會使用 Analytics。

如要進一步瞭解 Firebase 專案,請參閱「瞭解 Firebase 專案」一文。

升級至 Blaze 定價方案

如要使用 Cloud Functions for Firebase,您必須將 Firebase 專案升級至 Blaze 定價方案。也就是說,您將 Google Cloud Billing 帳戶附加至專案。你必須提供信用卡或其他付款方式。

所有 Firebase 專案 (包括 Blaze 方案中的專案) 仍可存取 Cloud Functions 的免費用量配額。本程式碼研究室提供的步驟屬於免費用量限制。不過,您會看見 Cloud Storage 收取小額費用 ( 約 $0.03),這會用於託管您的 Cloud Functions 建構映像檔。

4. 安裝 Firebase CLI

Firebase CLI (指令列介面) 可讓您部署 Cloud Functions。

安裝 Firebase CLI 的方法有很多種,具體取決於您的作業系統和用途。如果您也使用 Cloud Functions,下列步驟說明最常見的選項。

  1. 確認您已安裝 npm,該程式通常會隨附 Node.js
  2. 執行下列 npm 指令安裝或升級 CLI:
$ npm -g install firebase-tools
  1. 執行下列指令,驗證 CLI 已正確安裝:
$ firebase --version

確認 Firebase CLI 版本為 9.0.0 以上版本,以便具備 Cloud Functions 所需的所有最新功能。如果沒有,請執行 npm install -g firebase-tools 進行升級,如上所示。

  1. 執行下列指令來授權 Firebase CLI:
$ firebase login
  1. 在 shortcuts-functions-start 目錄中設定 Firebase CLI 以使用 Firebase 專案。執行下列指令、選取專案 ID,然後按照操作說明進行。系統提示時,您可以選擇任何別名,例如 codelab 做為執行個體。
$ firebase use --add

5. 函式目錄

現在,請使用 Cloud Functions 專用 Firebase SDK 新增功能,為遊戲「拼字檢查」建構後端。

Cloud Functions 可讓您擁有在雲端執行的程式碼,不必設定伺服器。本程式碼研究室將說明如何建構函式來回應 Firebase 驗證、Cloud Storage 和 Firebase 即時資料庫事件。首先介紹驗證

使用 Cloud Functions 專用的 Firebase SDK 時,函式程式碼預設會位於 functions 目錄下 (預設)。為了方便起見,我們建立了 functions/index.js 檔案,來存放程式碼。您可以先檢查 functions 目錄,再執行後續步驟。

$ cd functions
$ ls

函式程式碼也是 Node.js 應用程式,因此需要使用 package.json,可提供應用程式的部分相關資訊並列出依附元件。

如果您不熟悉 Node.js,可以先進一步瞭解相關資訊,再繼續本程式碼研究室。

package.json 檔案已列出兩個必要的依附元件:適用於 Cloud Functions 的 Firebase SDKFirebase Admin SDK。如要在本機安裝,請從 functions 目錄執行 npm install

$ npm install

現在,我們來看看 index.js 檔案:

index.js

/**
 * Copyright 2021 Google Inc. All Rights Reserved.
 * ...
 */
// TODO(DEVELOPER): Import the Cloud Functions for Firebase and Firebase Admin modules here. Also import the Actions SDK here.
// TODO(DEVELOPER): Write the getWordDetailsFromDictionaryAPI function here.
// TODO(DEVELOPER): Write the createSpellingPracticeWord function here.
// TODO(DEVELOPER): Write the app Handle getSpellingWordList function here.
// TODO(DEVELOPER): Write the app Handle getSpellingWord function here.
// TODO(DEVELOPER): Write the app Handle repeatSpellingWord function here.
// TODO(DEVELOPER): Write the app Handle definitionOfSpellingWord function here.
// TODO(DEVELOPER): Write the app Handle verifySpellingWord function here.

您必須先匯入必要模組,然後編寫四個函式來取代 TODO。繼續本程式碼研究室的下一個步驟,即可匯入模組。

6. 匯入必要模組

本程式碼研究室需要三個模組。

  • firebase-functions 模組讓我們能夠為 Cloud Functions 編寫觸發條件
  • 有了 firebase-admin 模組,我們就能在具備管理員存取權的伺服器上使用 Firebase 平台,例如寫入 Cloud Firestore。
  • Actions SDK Node.js 執行要求程式庫執行了 Google 助理適用的 Actions SDK 處理常式。
  1. 執行下列 npm 指令安裝 Actions SDK:
$ npm install @assistant/conversation
  1. index.js 檔案中,將第一個 TODO 替換成以下內容。

這些變更會匯入各個必要模組。

此外,在 Cloud Functions 環境或其他 Google Cloud 容器部署時,您也可以自動設定 Firebase Admin SDK。我們在下列變更中呼叫 admin.initializeApp(); 時,就會發生這種情況。

index.js

/**
 * Copyright 2021 Google Inc. All Rights Reserved.
 * ...
 */

// Import the Actions SDK
const {conversation} = require('@assistant/conversation');
const https = require('https');
const app = conversation();
const cors = require('cors')({origin: true});

// Import the Firebase SDK for Cloud Functions.
const functions = require('firebase-functions');
// Import and initialize the Firebase Admin SDK.
const admin = require('firebase-admin');
admin.initializeApp();
// To access Cloud Firestore
const db = admin.firestore();
// TODO(DEVELOPER): Write the getWordDetailsFromDictionaryAPI function here.
// TODO(DEVELOPER): Write the createSpellingPracticeWord function here.
// TODO(DEVELOPER): Write the shuffleWordList function here.
// TODO(DEVELOPER): Write the app Handle getSpellingWordList function here.
// TODO(DEVELOPER): Write the app Handle getSpellingWord function here.
// TODO(DEVELOPER): Write the app Handle repeatSpellingWord function here.
// TODO(DEVELOPER): Write the app Handle definitionOfSpellingWord function here.
// TODO(DEVELOPER): Write the app Handle verifySpellingWord function here.

現在,我們來使用函式新增商業邏輯,以支援 Google 助理動作。

7. 建立函式

取得字詞定義並寫入 Cloud Firestore

您將使用 dictionaryapi.dev 公用 API 取得字詞定義。

index.js 檔案中,將 getWordDetailsFromDictionaryAPI 的 TODO 替換為下列內容:

index.js

// Retrieves word definition and audio pronunciation from api.dictionaryapi.dev service
// Function uses service provided by https://dictionaryapi.dev/
async function getWordDetailsFromDictionaryAPI(word) {
  let responseData="";
  let req = https.request({
    host: 'api.dictionaryapi.dev',
    port: 443,
    path:'/api/v2/entries/en/' + word,
    method:'GET'
  }, (res) => {
    res.setEncoding('utf8');
    res.on('data', d => {
        responseData+=d;
    })
    res.on('end',function(){
        let object = JSON.parse(responseData)
        const wordListRef = db.collection('wordlist');
        wordListRef.doc(object[0].word).set(
          object[0]
        );
       return responseData;
     });
  });
  req.end();
}

新增 Cloud Firestore 觸發條件

接下來,您將建立 Cloud 函式,每當在 Cloud Firestore 建立新文件時就會觸發這個函式。它會呼叫 dictionaryapi.dev API,透過我們剛才編寫的 getWordDetailsFromDictionaryAPI 函式取得字詞定義。

index.js 檔案中,將 createSpellingPracticeWord 的 TODO 替換為下列內容:

index.js

// Firestore 觸發條件,可透過 getWordDetailsFromDictionaryAPI 擷取每個新 Firestore 文件的字詞定義

exports.createSpellingPracticeWord = functions.firestore
  .document('wordlist/{word}')
  .onCreate((snap, context) => {
    const newValue = snap.data();
    const word = newValue.word;
    getWordDetailsFromDictionaryAPI(word);
});

取得遊戲字詞清單

您可以編寫 Cloud 函式,為 Google 助理從 Cloud Firestore 擷取拼字練習字詞清單。為此,我們要使用應用程式處理常式。

index.js 檔案中,將 getSpellingWordList 的 TODO 替換為下列內容。

只要在特殊 app.handle 中加入這個函式,即可讓 Google 助理存取該函式。

index.js

// Store the list of spelling words in Assistant session
app.handle('getSpellingWordList', conv => {
  const wordListRef = db.collection('wordlist').limit(50);
  const snapshot = wordListRef;

  if (snapshot.empty) {
    console.log('No matching documents.');
    return;
  }
  VocabularyList = []

  return snapshot.get().then(snapshot => {
    snapshot.forEach(doc => {
      if (doc.data().word) {
          let definition = 'unknown';
          let audio = 'unknown';
          try {
            if(doc.data().hasOwnProperty('meanings')) {
              if(doc.data().meanings[0].hasOwnProperty('definitions')) {
                  definition = doc.data().meanings[0].definitions[0].definition;
              }
            }
            if(doc.data().hasOwnProperty('phonetics')) {
              if(doc.data().phonetics.length > 0)
                audio = doc.data().phonetics[0].audio;
            }
          } catch (error) {
            console.log(error);
          }

          let obj = {
            word: doc.data().word,
            answer: doc.data().word.split("").join(" "),
            definition: definition,
            audio: audio
          }
          VocabularyList.push(obj);
      }
      // Shuffle the array
      let currentIndex = VocabularyList.length, temporaryValue, randomIndex;
      while (0 !== currentIndex) {
        randomIndex = Math.floor(Math.random() * currentIndex);
        currentIndex -= 1;
        temporaryValue = VocabularyList[currentIndex];
        VocabularyList[currentIndex] = VocabularyList[randomIndex];
        VocabularyList[randomIndex] = temporaryValue;
      }
      conv.session.params.vocabWord = VocabularyList;
      conv.session.params.vocabWordIndex = 0;
    });
  });
})

透過 Google 助理工作階段瞭解特定字詞

您可以編寫 Cloud 函式,從字詞清單中傳回下一個拼字字詞。

index.js 檔案中,將 getSpellingWord 的 TODO 替換為下列內容:

index.js

// Returns a spelling practice word to Google Assistant and uses Speech Synthesis Markup Language (SSML) to format the response
app.handle('getSpellingWord',  conv => {
  if (!conv.session.params.vocabWord.empty) {
    conv.session.params.vocabWordIndex+=1;
    const ssml = '<speak>' +
    '<audio src="'+ conv.session.params.vocabWord[conv.session.params.vocabWordIndex].audio +'">Use phonetics to spell the word.</audio> ' +
    '</speak>';
    conv.add(ssml);
  }
  else
    conv.add('Great job! You completed the Spelling practice');
});

啟用遊戲再重複這個字詞

您可以編寫與遊戲目前字詞重複的 Cloud 函式。

index.js 檔案中,將 repeatSpellingWord 的 TODO 替換為下列內容:

index.js

// Returns current spelling word
app.handle('repeatSpellingWord',  conv => {
  if (!conv.session.params.vocabWord.empty) {
    const ssml = '<speak>' +
    '<audio src="'+ conv.session.params.vocabWord[conv.session.params.vocabWordIndex].audio +'">Use phonetics to spell the word. </audio> ' +
    '</speak>';
    conv.add(ssml);
  }
  else
    conv.add('Great job! You completed the Spelling practice');
});

取得字詞定義

您可以編寫 Cloud 函式,提供遊戲目前字詞的定義。

index.js 檔案中,將 definitionOfSpellingWord 的 TODO 替換為下列內容:

index.js

// Returns spelling word definition from Assistant session parameter
app.handle('definitionOfSpellingWord',  conv => {
  conv.add( 'It means ' + conv.session.params.vocabWord[conv.session.params.vocabWordIndex].definition);
});

檢查使用者的拼字回應

您可以編寫 Cloud 函式,驗證使用者對遊戲目前字詞的發音方式的回應。

index.js 檔案中,將 verifySpellingWord 的 TODO 替換為下列內容:

index.js

// Verifies user spelling response
app.handle('verifySpellingWord', conv => {
  try {
    userResponse = conv.intent.params.userresponse.resolved.join("");
    if (userResponse.toLowerCase() === conv.session.params.vocabWord[conv.session.params.vocabWordIndex].word.toLowerCase()) {
      conv.add('You are correct. Say next to continue.');
    }
    else {
      conv.add('Sorry, wrong answer. The correct answer is ' + conv.session.params.vocabWord[conv.session.params.vocabWordIndex].answer + ' . Say next to continue.');
    }
  } catch (error) {
    conv.add('Sorry. I did not understand your response' );
  }
});
exports.ActionsOnGoogleFulfillment = functions.https.onRequest(app);

部署所有函式

您必須將 Cloud Functions 部署至 Firebase,系統才會啟用相關函式。

spelling-functions-start 目錄的根目錄中執行下列指令:

$ firebase deploy --only functions

以下是控制台輸出內容:

i  deploying functions
i  functions: ensuring necessary APIs are enabled...
⚠  functions: missing necessary APIs. Enabling now...
i  env: ensuring necessary APIs are enabled...
⚠  env: missing necessary APIs. Enabling now...
i  functions: waiting for APIs to activate...
i  env: waiting for APIs to activate...
✔  env: all necessary APIs are enabled
✔  functions: all necessary APIs are enabled
i  functions: preparing functions directory for uploading...
i  functions: packaged functions (X.XX KB) for uploading
✔  functions: functions folder uploaded successfully
i  starting release process (may take several minutes)...
i  functions: creating function createSpellingPracticeWord(us-central1)...
✔  functions[createSpellingPracticeWord(us-central1)]: Successful create operation.
i  functions: creating function ActionsOnGoogleFulfillment(us-central1)...
✔  functions[ActionsOnGoogleFulfillment(us-central1)]: Successful create operation.

✔  Deploy complete!
Project Console: https://console.firebase.google.com/project/spelling-practice-1234/overview

記下 ActionsOnGoogleFulfillment 函式 Http 端點網址,供日後使用。如要取得端點,請開啟 Firebase 控制台,然後按一下「spelling-practice」專案。開啟函式資訊主頁,查看函式端點。

332cb0437411a242.png

您已新增所有必要函式。現在來設定 Cloud Firestore

8. 啟用 Cloud Firestore

您必須啟用 Cloud Firestore。

在 Firebase 控制台的「建構」部分,按一下「Firestore」。接著,按一下「建立資料庫」

5c0b4abf4410ffcf.png

Cloud Firestore 資料的存取權是由安全性規則控管。首先,您必須設定資料的一些基本規則。點選「Firestore」,在 Firebase 控制台的「規則」分頁中新增下列規則,然後點選「發布」

以下規則會限制資料只能存取已登入的使用者,避免未經驗證的使用者讀取或寫入資料。

rules_version = '2';
service cloud.firestore {
  match /databases/{database}/documents {
    match /{document=**} {
      //
      // WARNING: These rules are insecure! We will replace them with
      // more secure rules later in the codelab
      //
      allow read, write: if request.auth != null;
    }
  }
}

9. 將拼字字詞資料新增至 Cloud Firestore

在這個步驟中,您需要將拼字字詞資料寫入 Cloud Firestore,以便產生 Google 助理和遊戲的字詞清單。

Cloud Firestore 資料會以集合、文件、欄位和子集合的形式呈現。系統會將遊戲的每個字詞儲存為專屬文件,並儲存在名為 wordlist 的頂層集合中。Firestore 集合中的每個新文件都會觸發 createCraftingPracticeWord 函式,藉此從 Dictionary API 服務取得字詞詳細資料。

建立 Cloud Firestore 集合

  1. 前往 Firebase 控制台中的「Cloud Firestore」專區。
  2. 按一下「+ 開始珍藏內容」
  3. 在「集合 ID」文字方塊中輸入 wordlist,然後點選「下一步」

1b4ccadb90f52f02.png

接下來,我們要建立一份「agreement」字詞的文件

  1. 在「文件 ID」文字方塊中輸入 agreement
  2. 在「Field」文字方塊中輸入 word,並在「Value」文字方塊中輸入 agreement
  3. 按一下 [儲存]

379037e011e8511e.png

將這份文件新增至 Cloud Firestore 時,系統會觸發 createpelingPracticeWord 函式來擷取字詞的定義詳細資料。如要加入更多字詞 (例如,我們、汽車、真實、告訴、更好的、通勤...),可以為每個字詞建立新文件。

10. 設定「Google 助理」

以下各節將說明如何設定 Google 助理開發環境及建立 Actions 專案。

檢查 Google 權限設定

如要測試您在本程式碼研究室中建構的動作,請啟用必要權限,模擬工具可以存取您的動作。如要啟用權限,請按照下列步驟操作:

  1. 前往「活動控制項」頁面。
  2. 登入 Google 帳戶 (如果您尚未登入的話)。
  3. 啟用下列權限:
  • 網路和應用程式活動
  • 包括「網頁和」應用程式活動:勾選「包括 Chrome 歷史記錄以及採用 Google 服務的網站、應用程式和裝置中的活動記錄」旁的核取方塊。

c988e1e639e6d6e1.png

建立 Actions 專案

Actions 專案是 Action 的容器。如要為本程式碼研究室建立 Actions 專案,請按照下列步驟操作:

  1. 開啟動作控制台
  2. 按一下「New Project」
  3. 接受服務條款

b174d45710b8086b.png

  1. 輸入或選取您透過 Firebase 控制台建立的「spelling-practice-codelab。(這個名稱僅供您內部參考,您稍後可以為專案設定外部名稱)。

a2951de5d2001fac.png

  1. 按一下「匯入專案」
  2. 在「您想建構哪一種動作?」畫面中,選取「自訂」資訊卡。
  3. 點選「下一步」。
  4. 選取「空白專案」資訊卡。
  5. 按一下「開始建構」
  6. 輸入「拼字檢查」做為顯示名稱,然後按一下「儲存」。

使用者透過叫用功能來與你的動作展開對話。舉例來說,使用者可以說出「Ok Google,幫我說拼字練習」這類指令,其中「拼字練習」顯示名稱,藉此叫用您的動作。

如要部署至正式環境,您的動作必須設有顯示名稱;不過,如要測試動作,則不需要定義顯示名稱。相反地,您可以在模擬器中使用「與我的測試應用程式交談」這個詞組叫用您的動作。

設定執行要求

對於您先前在本程式碼研究室中編寫及部署的 Cloud Functions,您需要將事件處理常式連線至 Google 助理。

如要設定執行要求,請按照下列步驟操作:

  1. 按一下側邊導覽列中的「Webhook」
  2. 選取「Https 端點」做為執行要求選項:

d523bf003e96e66f.png

  1. 在「HTTPs 端點」文字方塊中輸入函式的端點網址,然後按一下「儲存」。

be53e2cd0d914d54.png

在下一節中,您將在動作控制台中自訂主要叫用的提示。

設定主要叫用

您必須編輯主要叫用,定義使用者叫用動作後會發生什麼事。

根據預設,當您觸發叫用時,動作建構工具會提供一般提示 (「透過定義主要叫用開始建構動作」)。

如要修改動作在使用者叫用動作時傳回的提示,請按照下列步驟操作:

  1. 按一下導覽中的「主要叫用」

9ff088c04c995cde.png

  1. 勾選 Call your webhook,然後在文字方塊中新增事件處理常式名稱 getSpellingWordList
  2. 在程式碼編輯器中,將 speech 欄位中的文字換成以下歡迎訊息:Welcome to Spelling Practice

注意:您可以使用 YAMLJSON 格式編輯提示。

  1. 按一下 [儲存]

在模擬器中測試主要叫用

Actions 主控台提供名為模擬工具的網路工具,用於測試您的動作。此介面會模擬硬體裝置和相關設定,因此您可以像在智慧螢幕、手機、喇叭或 KaiOS 上執行動作一樣,展開動作。

如要在模擬工具中測試動作的主要叫用情形,請按照下列步驟操作:

  1. 按一下頂端導覽列中的「測試」,前往模擬器。
  2. 如要在模擬器中叫用動作,請在左上方的輸入欄位中輸入 Talk to Spelling Practice,然後按下鍵盤上的 Enter 鍵。

651fc8da1ac9aa0a.png

當您觸發動作的主要叫用時,Google 助理就會以您的自訂歡迎訊息回應。此時,Google 助理會在回應問候語後結束對話。

查看事件記錄

進入「測試」分頁時,右側面板會顯示事件記錄,其中以事件記錄的形式顯示對話記錄。每個事件記錄都會顯示對話期間發生的事件。如要查看事件記錄,請按一下活動前的灰色圖示。

您的動作目前有一項事件記錄,其中會顯示使用者的輸入內容 (「與 peing Practice」) 和動作的回應。以下螢幕截圖顯示動作的事件記錄:

A6fb192f94426824.png

11. 為拼字練習建立對話

您已經定義使用者叫用動作後會發生什麼事,現在可以建立「動作」的其餘對話。拼字練習有四個場景,必須啟用每個場景才能運作。啟用場景最常見的方式是設定動作,當使用者與場景中的某個意圖相符時,該意圖就會觸發並啟動其他場景的轉場效果。

從主要叫用轉換到開始場景

在本節中,您將建立名為 Start 的新場景,用於傳送提示給使用者,詢問他們是否要開始玩拼字練習。此外,您也會在主要叫用中,加入轉場效果至新的 Start 場景。

如要建立這個場景並新增轉場效果,請按照下列步驟操作:

  1. 按一下頂端導覽列中的「Develop」(開發)。接著,按一下左側導覽面板中的「主要叫用」
  2. 在右側的「Transition」部分點選下拉式選單,然後在文字欄位中輸入 Start

dd4f1807a57f794d.png

  1. 按一下「Add」(新增)。這項操作會建立名為 Start 的場景,並在動作向使用者傳送歡迎提示後,指示動作轉換至 Start 場景。
  2. 按一下左側導覽面板中的「場景」,即可查看場景清單。
  3. 在「場景」下方,點選「開始」即可查看 Start 場景。
  4. 在「Start場景的「進入」部分按一下「+」
  5. 選取「傳送提示」
  6. speech 欄位中的句子 (Enter the response that users will see or hear...) 替換成用來詢問使用者的問題:Use phonetic alphabet to spell the word. For example alpha for a, bravo for b, charlie for c etc. Do you want to continue?

建議方塊會為動作提供可點擊的建議,使用者在輸入時執行動作。在本節中,您將在剛設定的提示下方新增建議方塊 (Do you want to play

Spelling Practice

?),為螢幕裝置使用者提供支援。

如要在 Start 情境的提示中新增建議方塊,請按照下列步驟操作:

  1. Start 場景中,按一下程式碼編輯器下方的建議。這項操作會新增一個建議方塊。
  2. title 欄位中的 Suggested Response 替換為 'Yes'
  3. 使用相同的格式設定,手動新增標題為 'No''Help with Phonetics' 的建議方塊。程式碼應如下所示:
  4. 按一下 [儲存]

5ff2ecdc56801b91.png

在模擬工具中測試動作

此時,您的動作應從主要叫用轉換為「Start」場景,並詢問使用者是否要繼續操作。建議方塊也會顯示在模擬畫面中。

如要在模擬工具中測試動作,請按照下列步驟操作:

  1. 按一下導覽列中的「測試」,前往模擬工具。
  2. 如要在模擬工具中測試動作,請在輸入欄位中輸入 Talk to Spelling Practice
  3. 按下 Enter 鍵。您的動作應透過 Main invocation 提示和新增的 Start 情境提示回應:「歡迎來練習拼字練習。」使用拼音字母拼出字詞。例如 a 的 Alpha 值、b 的 bravo、為 c 的 charlie 等。你要繼續嗎?"

以下螢幕截圖顯示了這項互動:

338c9570b02a618e.png

  1. 按一下 YesNoHelp with Phonetics 建議方塊,即可回覆提示。(你也可以說出「是」「否」「語音輔助」,或在「輸入」欄位中輸入 YesNoHelp with Phonetics。)

當您回應提示時,您的動作會回應一則訊息,指出它無法理解您所輸入的內容:「抱歉,我沒聽清楚。可以請你再試一次嗎?」您尚未將 Action 設定為理解並回應「是」或「否」輸入內容,因此動作會將您輸入的內容與 NO_MATCH 意圖相符。

根據預設,NO_MATCH 系統意圖會提供一般回應,但您可以自訂回應,向使用者表明您不瞭解其輸入內容。當 Google 助理無法比對使用者輸入內容三次後,Google 助理就會結束使用者的對話。

新增「否」和「拼音」意圖

使用者現在能夠回應您動作所提出的問題,您就可以設定動作,瞭解使用者的回應 (「是」「否」「語音小幫手」)。在以下各節中,您會建立在使用者說出「是」、「否」或「語音說明」時比對的使用者意圖並將這些意圖新增至 Start 場景。我們會使用系統意圖 yes 並建立其他意圖。

建立「no」意圖

現在,您需要建立 no 意圖,瞭解並回覆不想玩遊戲的使用者。如要建立意圖,請按照下列步驟操作:

  1. 按一下導覽列中的「開發」
  2. 按一下導覽列中的「自訂意圖」,開啟意圖清單。
  3. 按一下意圖清單結尾的「+」(加號)。將新意圖命名為 no,然後按下 Enter 鍵。
  4. 按一下「no」,開啟「no意圖頁面。
  5. 在「Add train routes」(新增訓練詞組) 區段,按一下「Enter phrase」(輸入詞組) 文字方塊,然後輸入下列詞組:
  • No
  • N
  • I don't want
  • nope

98b0c9a7b67ea9b9.png

  1. 按一下 [儲存]

no 意圖新增至 Start 個場景

現在,動作可以瞭解使用者表示「否」或與「否」類似的結果 (例如「nope」)。您必須在 Start 場景中新增 no 使用者意圖,因為使用者會回應 Start 提示 (「歡迎使用拼字練習。使用拼音字母拼出字詞。例如 a 的 Alpha 值、b 的 bravo、為 c 的 charlie 等。你要繼續嗎?")。

如要為 Start 場景新增此意圖,請按照下列步驟操作:

  1. 按一下導覽列中的「Start」場景。
  2. 在「使用者意圖處理」旁的 Start 情境中,按一下「+ (加號)」
  3. 在「Intent」(意圖) 區段的下拉式選單中,選取「no」

51f752e78c8b4942.png

  1. 按一下「傳送提示」,然後將「speech欄位更新為以下文字:Good Bye

編輯器中的程式碼應如以下程式碼片段所示:

candidates:
  - first_simple:
      variants:
        - speech: >-
             Goodbye.
  1. 在「轉換」部分的下拉式選單中,選取「結束對話」
  2. 按一下 [儲存]

在模擬工具中測試 no 意圖

這時,您的動作就能瞭解使用者何時不想玩遊戲,並傳回適當的回應。

如要在模擬工具中測試這個意圖,請按照下列步驟操作:

  1. 按一下導覽列中的「測試」
  2. 在輸入欄位中輸入 Talk to Spelling Practice,然後按下 Enter
  3. 在「輸入內容」欄位中輸入 No,然後按下 Enter 鍵。或者,您也可以按一下「無建議」方塊。

7727a456b522f31b.png

將系統 YES 意圖新增至 Start 場景

現在,我們會將 SYSTEM 意圖「YES」新增至 Start 場景,因為使用者會回覆 Start 提示 (「歡迎使用拼字練習」。使用拼音字母拼出字詞。例如 a 的 Alpha 值、b 的 bravo、為 c 的 charlie 等。你要繼續嗎?")。

如要將這項使用者意圖新增至 Start 場景,請按照下列步驟操作:

  1. 按一下導覽列中的「Start」場景。
  2. 在「使用者意圖處理」旁的 Start 情境中,按一下「+ (加號)」
  3. 在「All System Intents」(所有系統意圖) 下方,在意圖下拉式選單中選取「YES」

f6cbe789cde49e8f.png

  1. 按一下「Call your Webhook」,然後將「event handler文字方塊更新為您先前建立的函式:getSpellingWordList
  2. 在「轉換」部分,按一下下拉式選單,然後選取「結束對話」
  3. 按一下 [儲存]

在模擬工具中測試 YES 意圖

這時,您的動作就能瞭解使用者何時想玩遊戲,並傳回適當的回應。

如要在模擬工具中測試這個意圖,請按照下列步驟操作:

  1. 按一下導覽列中的「測試」
  2. 如要在模擬工具中測試動作,請在「Input」欄位中輸入 Talk to Spelling Practice,然後按下 Enter 鍵。
  3. 在「輸入內容」欄位中輸入 Yes,然後按下 Enter 鍵。或者,也可以按一下 Yes 建議方塊。

您的動作會擷取所有拼字練習字詞清單,並儲存在工作階段中。如此,您的動作就會結束工作階段,因為您選取了 YES 意圖的 End conversation 轉換作業。

建立「Phonetics」意圖

如要建立 Phonetics 意圖,請按照下列步驟操作:

  1. 按一下導覽列中的「開發」
  2. 按一下導覽列中的「自訂意圖」,開啟意圖清單。
  3. 按一下意圖清單結尾的「+」(加號)。將新意圖命名為 phonetics,然後按下 Enter
  4. 按一下 phonetics 意圖,開啟 phonetics 意圖頁面。
  5. 在「Add train permissions」(新增訓練詞組) 部分中,按一下「Enter phrase」(輸入詞組) 文字方塊,然後輸入下列詞組:
  • how do I spell words
  • phonetics
  • help me with phonetics
  • phonetic alphabet

1455bdfca8dae46.png

  1. 按一下 [儲存]

phonetics 意圖新增至 Start 個場景

現在,動作可以瞭解使用者表示「拼音」意圖。您可以將 phonetics 使用者意圖新增到 Start 場景,因為使用者會回應 Start 提示 (「歡迎使用 拼字練習.使用拼音字母拼出字詞。例如 a 的 Alpha 值、b 的 bravo、為 c 的 charlie 等。你要繼續嗎?")。

如要將這項使用者意圖新增至 Start 場景,請按照下列步驟操作:

  1. 按一下導覽列中的「Start」場景。
  2. 在「使用者意圖處理」旁的 Start 情境中,按一下「+」(加號)。
  3. 在意圖下拉式選單中選取「phonetics」

67ee2e08000b2aee.png

  1. 在「轉換」部分點選下拉式選單,然後選取「結束對話」
  2. 按一下 [儲存]

從「開始場景」轉換至「拼字」場景

在本節中,您將建立名為「拼字」的新場景,提示使用者依照拼音字母拼出字詞。

如要建立這個場景並新增轉場效果,請按照下列步驟操作:

  1. 按一下頂端導覽列中的「Develop」(開發)。然後點選左側導覽面板中的「開始場景」
  2. 在「使用者意圖處理」部分,按一下「when actions.intent.YES is matched,然後在右側的「轉換」部分按一下下拉式選單,並在文字欄位中輸入 Spelling
  3. 按一下「Add」(新增)。這會建立名為 Spelling 的場景,並在比對出「YES」意圖後要求動作轉換至 Spelling 場景。
  4. 展開左側導覽面板中的「Scenes」,顯示場景清單。
  5. 在「場景」下方點選「拼字」即可查看 Spelling 場景。
  6. 在「Spelling場景的「進入」部分按一下「+」
  7. 按一下「Call your Webhook」,然後在事件處理常式文字方塊中輸入 getCraftingWord
  8. 選取「傳送提示」
  9. speech 欄位中的句子(Enter the response that users will see or hear...) 替換為 {}Webhook 會填入實際的提示。

建議方塊會為動作提供可點擊的建議,使用者在輸入時執行動作。

如要在 Spelling 情境的提示中新增建議方塊,請按照下列步驟操作:

  1. Spelling 場景中,按一下程式碼編輯器下方的建議。這項操作會新增三個建議方塊。
  2. title 欄位中的 Suggested Response 替換為 'Repeat'
  3. 使用相同的格式設定,手動新增標題為 'Skip' 的建議方塊。
  4. 使用相同的格式設定,手動新增標題為 'Quit' 的建議方塊。程式碼應如下所示:
  5. 按一下 [儲存]
suggestions:
      - title: 'Repeat'
      - title: 'Skip'
      - title: 'Quit'

e1d437f714ea1539.png

建立「Repeat」意圖

如要建立 repeat 意圖,請按照下列步驟操作:

  1. 按一下導覽列中的「開發」
  2. 按一下導覽列中的「自訂意圖」,開啟意圖清單。
  3. 按一下意圖清單結尾的「+」(加號)。將新意圖命名為 repeat,然後按下 Enter
  4. 按一下 repeat 意圖,開啟「definition意圖頁面。
  5. 在「Add train routes」(新增訓練詞組) 區段,按一下「Enter phrase」(輸入詞組) 文字方塊,然後輸入下列詞組:
  • one more time please
  • say the word again
  • repeat the word
  • tell me again
  • repeat

e61f0b9f80510bc9.png

  1. 按一下 [儲存]

repeat 意圖新增至 Spelling 個場景

現在,動作可以瞭解使用者何時表示「重複」意圖。您可以將 repeat 使用者意圖新增到 Spelling 場景,因為使用者會回應 Spelling 提示 (「使用拼音字母拼出字詞」)。

如要將這項使用者意圖新增至 Spelling 場景,請按照下列步驟操作:

  1. 按一下導覽列中的「拼字」場景。
  2. 在「使用者意圖處理」旁的 Spelling 情境中,按一下「+ (加號)」
  3. 在意圖下拉式選單中選取 [repeat] (重複)

5cfd623b25bedbed.png

  1. 勾選「Call your Webhook」核取方塊,並在事件處理常式文字方塊中輸入 repeatpelingWord,即可取得字詞定義。
  2. 勾選「傳送提示」
  3. speech 欄位中的句子 (Enter the response that users will see or hear...) 替換為「'」。Webhook 會填入實際的提示。

新增建議方塊至「比對重複時」

  1. 在「When Repeat to match」(「重複比對時」相符) 中在「使用者意圖處理」下方,按一下程式碼編輯器下方的「建議」。這項操作會新增三個建議方塊。
  2. title 欄位中的 Suggested Response 替換為 'Skip'
  3. 使用相同的格式,手動新增標題為 'Quit' 的建議方塊。程式碼應如下所示:
suggestions:
      - title: 'Skip'
      - title: 'Quit'

ab40e4b0c432b97c.png

  1. 按一下「儲存」

建立「definition」意圖

如要建立 definition 意圖,請按照下列步驟操作:

  1. 按一下導覽列中的「開發」
  2. 按一下導覽列中的「自訂意圖」,開啟意圖清單。
  3. 按一下意圖清單結尾的「+」(加號)。將新意圖命名為 definition,然後按下 Enter
  4. 按一下 definition 意圖,開啟 definition 意圖頁面。
  5. 在「Add train routes」(新增訓練詞組) 區段,按一下「Enter phrase」(輸入詞組) 文字方塊,然後輸入下列詞組:
  • I would like to know the definition
  • tell me the definition
  • what does it mean
  • meaning
  • definition
  • what is the definition?

c1b88a9c0b1ac082.png

  1. 按一下 [儲存]

definition 意圖新增至 Spelling 個場景

現在,動作可以瞭解使用者如何表示「定義」意圖。您可以將 definition 使用者意圖新增到 Spelling 場景,因為使用者會回應 Spelling 提示 (「使用拼音字母拼出字詞」)。

如要將這項使用者意圖新增至 Spelling 場景,請按照下列步驟操作:

  1. 按一下導覽列中的「拼字」場景。
  2. 在「使用者意圖處理」旁的 Spelling 情境中,按一下「+ (加號)」
  3. 在意圖下拉式選單中選取「定義」

646bdcac3ad3eb0c.png

  1. 勾選「Call your Webhook」,並在事件處理常式文字方塊中輸入 definitionOfCraftingWord,以取得字詞定義。
  2. 勾選「傳送提示」
  3. speech 欄位中的句子 (Enter the response that users will see or hear...) 替換為「‘`」。Webhook 會填入實際的提示。

將建議方塊新增至 Webhook 回應

  1. Start 場景中,按一下程式碼編輯器下方的「建議」。這項操作會新增三個建議方塊。
  2. title 欄位中的 Suggested Response 替換為 'Skip'
  3. 使用相同的格式,手動新增標題為 'Quit' 的建議方塊。程式碼應如下所示:
suggestions:
      - title: 'Skip'
      - title: 'Quit'

25227545839d933f.png

  1. 按一下 [儲存]

建立「skip」意圖

如要建立 skip 意圖,請按照下列步驟操作:

  1. 按一下導覽列中的「開發」
  2. 按一下導覽列中的「Intents」(意圖),開啟意圖清單。
  3. 按一下意圖清單結尾的「+」(加號)。將新意圖命名為 skip,然後按下 Enter
  4. 按一下 skip 意圖,開啟 skip 意圖頁面。
  5. 在「Add train routes」(新增訓練詞組) 區段,按一下「Enter phrase」(輸入詞組) 文字方塊,然後輸入下列詞組:
  • next word
  • go next
  • next
  • skip
  • skip word

d1c4908a3d7882f8.png

  1. 按一下 [儲存]

Skip 意圖新增至 Spelling 個場景

現在,動作可以瞭解使用者表示「略過」意圖。您可以將 skip 使用者意圖新增到 Spelling 場景,因為使用者會回應 Spelling 提示 (「使用拼音字母拼出字詞」)。

如要將這項使用者意圖新增至 Spelling 場景,請按照下列步驟操作:

  1. 按一下導覽列中的「拼字」場景。
  2. 在「使用者意圖筆跡」旁的 Spelling 情境中,按一下「+ (加號)」
  3. 在意圖下拉式選單中選取「skip」

5465f97542217964.png

  1. 在右側的「轉換」部分,點選下拉式選單並選取「Spelling

c8072485ca82bd3f.png

  1. 按一下 [儲存]

建立「quit」意圖

如要建立 Quit 意圖,請按照下列步驟操作:

  1. 按一下導覽列中的「開發」
  2. 按一下導覽列中的「Intents」(意圖),開啟意圖清單。
  3. 按一下意圖清單結尾的「+」(加號)。將新意圖命名為 Quit,然後按下 Enter
  4. 按一下 Quit 意圖,開啟「定義」意圖頁面。
  5. 在「Add train routes」(新增訓練詞組) 區段,按一下「Enter phrase」(輸入詞組) 文字方塊,然後輸入下列詞組:
  • I quit
  • Goodbye
  • Cancel
  • Exit
  • Quit

9916f77b8766541e.png

  1. 按一下「儲存」

Quit 意圖新增至 Spelling 個場景

現在,動作可以瞭解使用者表示「離開」意圖。您可以將 quit 使用者意圖新增到 Spelling 場景,因為使用者會回應 Spelling 提示 (「使用拼音字母拼出字詞」)。

如要將這項使用者意圖新增至 Spelling 場景,請按照下列步驟操作:

  1. 按一下導覽列中的「拼字」場景。
  2. 在「使用者意圖處理」旁的 Spelling 情境中,按一下「+ (加號)」
  3. 在意圖下拉式選單中選取「quit」

5f62fb18a3653d66.png

  1. 在右側的「轉換」部分,點選下拉式選單並選取「End conversation1ffbe35a7bbbb4b0.png
  2. 按一下 [儲存]

建立「phonetic_alphabet」類型

在本節中,您將建立名為 phonetic_alphabet 的新類型,以指定使用者可使用的拼音字母選項。此外,您也可以定義這些選項的幾個同義詞,以便在使用者說類似的文字時查詢。在後續部分中,您會將 phonetic_alphabet 類型新增至版位,指定要取得使用者回應。

如要建立 phonetic_alphabet 類型,請按照下列步驟操作:

  1. 按一下導覽列中的「開發」
  2. 在「類型」下方,點選「+ (加號)」
  3. 輸入 phonetic_alphabet,然後按下 Enter 鍵。
  4. 按一下 phonetic_alphabet 開啟選項。
  5. 在「這個類型支援哪些類型的值?」部分,選取「字詞和同義詞」選項。
  6. 在「Add 個項目」部分中輸入下列項目和對應的值:

a 鍵

alpha、apple、 amsterdam

b 鍵

Bravo, Butter、Baltimore

C

Charlie, cat, casablanca

d 鍵

delta、dog、denmark

E 鍵

echo, edward, edison

f

狐狸、狐狸、佛羅裡達

公克

高爾夫、喬治、加利波利

小時

飯店、哈里和哈瓦那

i

印度、墨水、義大利

j 鍵

juliette、johnny、jerusalem

K

公斤, 金, 公斤

l 鍵

利馬、愛、倫敦

分鐘

小麥、錢、馬達加斯加

N 鍵

11 月、新約克、南西

o 鍵

Oscar、Orange、Ooslo

papa, Paris, peter

Q

魁北克、皇后

R 鍵

羅馬、羅馬、羅伯特

塞爾拉、糖、聖地牙哥

探戈, 湯米, 特里波利

U 鍵

統一, 雨傘, 叔叔

V

victor、vinegar、Valencia

Whiskey、Waiam、washington

x 鍵

X 光

yankee、黃色、yorker

Z

zulu、斑馬、蘇黎世

鍵/值資料表看起來會像這樣:

5b5a5cd9fa557e1b.png

  1. 按一下 [儲存]

設定運算單元填充

接下來,您需要在拼字場景中設定運算單元填充。如要設定運算單元填充邏輯,請按照下列步驟操作:

  1. 按一下導覽列中的「拼字」場景。
  2. 在「運算單元填充」Spelling 場景中按一下「+」(加號)
  3. 在「輸入運算單元名稱」欄位中,新增 userresponse 做為版位名稱。
  4. 在「選取類型」下拉式選單中,選取「phonetic_alphabet」做為版位類型。
  5. 勾選「這個時段接受值清單」
  6. 勾選「這個時段是必要項目」
  7. 選取「自訂運算單元值寫回」選項,並在工作階段參數文字方塊中輸入使用者回應。

ba57a419877a07f3.png

  1. 按一下 [儲存]

在「Spelling」畫面新增條件

如要在 Spelling 場景中新增條件,請按照下列步驟操作:

  1. 按一下導覽列中的「拼字」場景。
  2. 在「條件」旁的 Spelling 情境中,按一下「+」(加號)
  3. 輸入「scene.slots.status == "FINAL"做為條件
  4. 勾選「Call your Webhook」,在事件處理常式文字方塊中輸入「verifypelingWord」,即可驗證使用者回應。
  5. 勾選「傳送提示」
  6. speech欄位 (Enter the response that users will see or hear...) 中的句子替換為 {}。Webhook 會填入實際的提示。

將建議方塊新增至 Webhook 回應

  1. Start 場景中,按一下程式碼編輯器下方的「建議」。這項操作會新增三個建議方塊。
  2. title 欄位中的 Suggested Response 替換為 'Next'
  3. 使用相同的格式,手動新增標題為 'Quit' 的建議方塊。程式碼應如下所示:
suggestions:
      - title: 'Next'
      - title: 'Quit'

ac3d7a9366ebc1b1.png

  1. 按一下 [儲存]

12. 在模擬器中測試拼字練習

如要在模擬工具中測試動作,請按照下列步驟操作:

  1. 按一下導覽列中的「測試」,前往模擬工具。
  2. 如要在模擬工具中測試動作,請在輸入欄位中輸入 Talk to Spelling Practice
  3. 按下 Enter 鍵。動作應以 Main invocation 提示和新增的 Start 情境提示回應:「歡迎使用拼字練習。」使用拼音字母拼出字詞。例如 a 的 Alpha 值、b 的 bravo、為 c 的 charlie 等。你要繼續嗎?"
  4. 說出「是」繼續操作
  5. 模擬器會播放字詞音效
  6. 您可以使用拼音字母拼出字詞。例如,如果說 better,請說出或輸入「bravo echo tango tango echo romeo」
  7. 模擬器會傳回正確或不正確的回應。
  8. 說出「繼續」前往下一個字詞,或是說出「退出」結束遊戲迴圈。

13. 恭喜

恭喜,你已成功建立「拼字練習」遊戲!

您現已瞭解使用 Cloud Firestore、Cloud Functions 和 Google 助理 Action Builder 建構遊戲所需的重要步驟。

涵蓋內容

  • 如何與 Cloud Firestore 互動
  • 如何使用運算單元向使用者收集資料
  • 如何處理使用者的輸入內容並傳回回應
  • 如何使用條件在場景中新增邏輯
  • 如何新增遊戲迴圈

其他學習資源

您可以探索下列資源,瞭解如何建構適用於 Google 助理的動作:

清理專案 [建議]

如要避免產生可能產生的費用,建議您移除不想使用的專案。如要刪除您在本程式碼研究室中建立的專案,請按照下列步驟操作:

  1. 如要刪除 Firebase 專案和資源,請完成「關閉 (刪除) 專案」一節所列的步驟。

注意事項:請務必在 Google Cloud 控制台的「設定」頁面,選取正確的要刪除的專案。

  1. 選用:如要立即將專案從 Actions 主控台中移除,請完成刪除專案一節中列出的步驟。如未完成這個步驟,系統將在約 30 天後自動移除專案。

追蹤 @ActionsOnGoogle &@Firebase 追蹤我們的最新消息,並透過貼文和 #GoogleIO 分享你的成果!