如何使用Twilio,Python和Google表格(帶有Free&nbspCode)製作可擴展的SMS聊天機器人

我們中的許多人正在幫助面臨困境的企業,或者我們自己正在面對困境的企業。如果您在遇到麻煩的公司(或客戶)中工作,則使用SMS聊天機器人可能是一種讓您脫離常規解決方案列表並以完全不同的方式幫助他們成功的方法。如果您是尋找工作的營銷人員,那麼將其添加到您的技能列表中可能意味著您在許多通常的門關閉或打開新的門的同時,保持事情的順利進行。

你會得到什麼

在這篇文章中,我為您提供了說明和代碼,它們不僅可以生成一個代碼,還可以生成一系列可以由Google Sheets管理的基於文本的聊天機器人。

此處的示例設置為可與餐廳一起使用,但可適用於需要接收訂單,根據庫存/菜單檢查訂單並記下要履行的任何業務。

一旦建立了系統,就無需為新業務創建新的基於SMS的聊天機器人的編碼。另外,該企業將能夠通過簡單地更新Google表格來管理關鍵詳細信息(如來料訂單和菜單),從而使所有這些功能比大多數其他選項更易於訪問。

但是首先,一些背景。

一些背景

2017年9月,作為我在Distilled的第一個大型激情項目之一,我寫了一篇Moz博客文章,告訴人們如何製作聊天機器人並給出一些示例代碼

今年四月,我收到了一封來自亞歷山大·西爾維斯特(Alexandre Silvestre)的電子郵件。亞歷克斯(Alex)發起了「一項非營利性的工作,以幫助當地的小企業主渡過這些充滿挑戰的時代,挽救儘可能多的工作,並繼續為我們的社區服務,同時幫助平緩曲線。」

這項工作始於專註於餐廳。亞歷克斯找到了我的2017年職位(天哪,內容營銷有效!),問我是否可以幫助他的團隊構建聊天機器人。我們就該漫遊器達成了一些基本要求:

  • 它必須完全在簡訊中工作(如果訂單非常複雜,則必須能夠直接與餐廳打個電話)。
  • 運行它必須儘可能接近免費。
  • 餐館必須能夠檢查訂單,更新菜單等,而無需設置特殊帳戶。

我們達成一致的解決方案包括三個部分:

  • Twilio(收費):提供電話號碼並處理大部分對話。
  • Google Cloud Functions(半免費):調用URL時,它將運行代碼(包括更新餐廳的資料庫)並返迴響應。
  • Google表格(免費):我們的資料庫平台。我們有一個工作表,其中列出了使用我們的聊天機器人的所有業務,並鏈接到每個業務的各個Google表格。

我將依次介紹這些組件,並告訴您如何使用它們。

如果您要返回本文,或者只需要一個領域的幫助,請隨時跳到您感興趣的特定部分:

價錢

這一切應該都便宜得多-我說的是每張訂單四美分。

即使這樣,也要始終確保所有定價警報都通過您主動監控的電子郵件地址發送。

當您剛開始執行此操作或進行了更改(例如添加新功能或新業務)時,請確保在接下來的幾周內重新檢查您的信用,以了解發生了什麼。

特威里奧

本地Twilio電話號碼的費用約為每月$ 1.00。發送和接收文本的費用約為0.0075美元,而Twilio Studio(我們用來做很多「對話」的費用)每次激活時的費用為0.01美元(每月前1000個免費)。

因此,假設您每月有2500個文本訂單,而每個訂單大約要處理5條文本消息,那麼每月的總費用約為100美元。

Google表格

Google表格是免費的,而且很棒。Google表格萬歲。

Google Cloud功能

Google在此處共享完整的定價詳細信息,但要了解的重要事項是:

1.促銷信用

您將獲得長達一年的免費試用期,其中包括$ 300的促銷信用,所以它將在花您的錢之前就花掉它。在一個月的測試結束時,我們已支出$ 0.00(包括促銷贈金)。那是因為還有每月的免費津貼。

2.免費津貼和定價結構

除了免費信用外,Google每月都會提供免費津貼。如果我們假設每個訂單大約需要激活我們的代碼5次,並且每次運行代碼最多需要五秒鐘(這是一段時間,但有時Google Sheets速度很慢),那麼我們每個月可能會收到多達40萬個訂單我們投入了促銷信用。

特威里奧

Twilio是一個付費平台,可讓您購買電話號碼,並讓該號碼根據輸入自動發送某些回復。

如果您不想閱讀有關Twilio的更多信息,而只想要免費的Twilio聊天機器人流程,就在這裡。

步驟1:購買Twilio電話號碼

購買電話號碼後,您可以收到該號碼的文字,然後將在您的Twilio帳戶中對其進行處理。您也可以通過該號碼發送簡訊。

步驟2:找到您的電話號碼

您可以通過單擊左上角的Twilio菜單,然後單擊「電話號碼」來查看購買的電話號碼列表。或者,您可以轉到電話號碼/傳入

5f28657ee06267-68623.jpg

一旦看到列出的電話號碼,請記下它。

步驟3:建立Studio流程

Studio是Twilio的拖放編輯器,可讓您創建對話的結構。工作室「流程」只是您已建立的特定對話的名稱。

再次單擊Twilio菜單,然後單擊「運行時」下的「 Studio」,即可進入Twilio Studio。

5f28657ee06267-9228.png

通過單擊「創建流」來創建新流。

創建新流程時,您可以選擇從頭開始,也可以使用內置選項之一為您創建流程(儘管它們不會像我所使用的模板那樣深入)在這裡分享)。

如果要使用我和Alex構建的流的版本,請選擇「從JSON導入」,然後單擊「下一步」。然後,下載此文件並將內容複製到出現的框中。

確保它以一個大括弧開頭,以一個大括弧結尾。出現的框將自動包含{},並且如果您在粘貼之前不刪除它們,則會加倍,並且它不會接受您的輸入。

如果一切順利,將為您提供如下流程:

5f28657fa5e045-166158.jpg

您可能會問:彩色義大利面的糾結到底是什麼聖物?

那就是我們創建的Twilio Studio流程,不用擔心,它基本上會分解為一系列多項選擇題,每個問題的答案將決定您下一步要去哪裡。

您可以在畫布上看到的所有內容都是Twilio Studio小部件庫中的小部件,並與「如果是,那麼是」類型條件連接在一起。

Studio Flow流程

在我們進入過程中的特定塊之前,下面是發生的情況的概述:

  1. 客戶向我們的Twilio號碼發送消息
  2. 根據發送的具體號碼,我們查找與其關聯的餐廳。然後,我們使用餐廳的名稱和保存的菜單向顧客發送消息。
  3. 如果客戶嘗試下單,我們會致電餐廳
  4. 如果客戶從我們的菜單中選擇某種東西,我們會詢問他們的名字,然後將其訂單記錄在該餐廳的表中,並告訴他們何時到達取貨
  5. 當/當用戶消息告訴我們他們在餐館外面時,我們詢問他們是否在步行/對他們的車輛的描述。我們將車輛描述記錄在同一張餐廳表中。

讓我們看看一些示例構建基塊吧?

初始觸發
5f2865805de068.84592842.png

初始觸發器會在每個流程的開始出現,並根據是簡訊,電話還是代碼正在訪問來拆分傳入的聯繫人。

「傳入消息」表示該聯繫人是通過簡訊發送的。我們現在只需要擔心這一點,所以讓我們集中在左手邊。

記錄我們正在開始新互動的事實
5f28658103de91.67702467.png

接下來,我們使用「設置變數」塊,您可以從小部件庫中獲取該塊。

「設置變數」塊使我們可以保存記錄信息,以備日後參考。例如,我們首先設置交互的「階段」。我們說階段是「開始」,就像我們處於互動的開始一樣。稍後,我們將在Studio和外部代碼中檢查stage的值是什麼,以便我們知道什麼時候做什麼。

5f286581c963d9.61528866.png

獲取我們的菜單

我們假設如果有人向我們發送了消息,觸發了聊天機器人,他們正在尋求訂購,因此下一步就是確定適用的菜單。

現在,我們可以直接將菜單寫到Studio中,並說只要有人向我們發送消息,我們就會以相同的選項列表進行響應。但這有幾個問題。

首先,這意味著如果我們要為多個餐廳進行設置,則必須為每個餐廳創建一個新流程。 

更大的問題是餐館經常更改菜單。如果我們希望這可以為許多不同的餐廳提供,那麼我們就不想花費所有時間在餐廳用完所有食材時手動更新Twilio。

因此,我們真正需要的是餐廳能夠列出自己的菜單。這就是Google表格的用武之地,但是我們稍後再討論。在Twilio中,我們只需要能夠詢問外部信息並將該外部信息轉發給用戶。為此,我們使用Webhook小部件:

5f28658253e999.92379539.png

這個小部件向URL請求,獲取響應,然後讓我們在消息和流中使用響應的內容。

如果對URL的請求成功,則Twilio將自動繼續執行成功步驟,否則我們可以將其設置為發送帶有「失敗」選項的「糟糕,出了點問題」響應。

在這種情況下,我們的Webhook將向Google Cloud函數URL發出請求(稍後會詳細介紹)。我們發送的請求將包含一些有關用戶以及我們需要代碼做什麼的信息。信息將採用JSON格式(與我上面共享的導入Twilio流的格式相同)。

我們的JSON將包含已發送消息的特定Twilio電話號碼,我們將使用該號碼來區分餐廳以及與我們聯繫的電話號碼。它還將包含我們收到的文本消息的內容以及我們之前設置的「階段」,因此代碼可以知道用戶在尋找什麼。

5f286582e6d0c0.15470116.png

然後,代碼將做一些事情(稍後再介紹)並返回其自身的信息。然後,我們可以告訴Twilio在消息中使用部分響應。

發送消息以回應

接下來,我們可以使用收到的信息來構造並向用戶發送消息。Twilio會記住您正在與之通話的號碼,並將您的消息發送到該號碼。

5f2865837a95a1.59446647.png

這是「發送並等待回復」窗口小部件,這意味著一旦發送了此消息,Twilio將假定對話仍在繼續而不是在此結束。

在這種情況下,我們正在寫歡迎信息。我們可以只寫簡單的內容,但是我們想使用從Webhook小部件獲得的一些變數。我們將特定的Webhook小部件稱為「 get_options」,因此我們可以通過編寫以下內容來訪問從中獲取的內容:

{{widgets.get_options

響應以JSON返回,幸運的是Twilio會自動將其分解為我們。 

我們可以通過以下方式訪問響應的各個部分:編寫「已分析」,然後在響應中給我們提供該信息的標籤。就這樣,代碼的響應看起來像這樣:

{「名稱」:restaurant_name,

「 dishes_string」:「您可以選擇Margherita披薩,夏威夷比薩,素食比薩」

「附加」:「大,中,小」}

我們通過編寫「 {{widgets.get_options.parsed.dishes_string}}」來獲得可用菜單,然後在下面編寫消息,該消息將發送給與機器人聯繫的人:

5f286584231070.12068786.png

根據消息做出決定

我們不能假設每個人都將以完全相同的方式使用該機器人,因此我們需要能夠根據特定條件更改我們的工作。「基於…拆分」小部件是我們如何選擇某些條件並設置滿足條件的方法。

5f286584c9e565.37848347.png

在這種情況下,我們使用對上一條消息的響應內容,可以使用{{options_follow_up.inbound.Body}}訪問該消息。「 Options_follow_up」是我們剛才談到的「發送並等待」小部件的名稱,「入站」表示響應,「正文」表示其中的文本。

然後我們設置一個條件。如果用戶以「其他」,「否」,「幫助」等類似的方式進行響應,他們將被轉移到另一條軌道上以打電話。如果他們回答未列出的任何內容,則可能是他們在嘗試訂購,因此我們接受他們的訂購,並使用我們的代碼進行檢查:

5f2865858b1707.17057050.png撥打電話

如果用戶說他們想要菜單外的東西,我們需要與餐廳打個電話。為此,我們首先致電用戶:

5f286586528758.82167270.png5f28658711bb51.59889976.png

然後,當他們接聽時,將該呼叫連接到我們已經在工作表中查詢過的餐廳號碼:

5f2865879b3cb5.85482516.png5f28658859b2d2.96616536.png

步驟4:為此電話號碼選擇您的工作室流程

請按照第二步中的說明返回購買的電話號碼的特定列表。然後滾動到底部,然後選擇您創建的Studio Flow。

5f286588de8570.32885994.pngGoogle表格

該聊天機器人使用兩個Google表格。

免費查閱表

查找表包含Twilio電話號碼,已分配給他們的餐廳的列表以及保存該餐廳詳細信息的Google表格的URL,以便我們知道在哪裡查找。

您需要創建工作表的副本才能使用它。我在共享的表格中添加了一行,解釋了每一列。當您知道自己在做什麼時,可以將其刪除。

screen-shot-2020-08-04-at-1-53792.jpg

免費示例餐廳表

特定於餐廳的工作表是我們在一系列標籤中包含有關餐廳的所有信息的地方。您需要創建工作表的副本才能使用它。 

訂單

訂單標籤主要由我們的代碼使用。它將自動輸入訂單時間,客戶名稱,客戶電話號碼和訂單詳細信息。默認情況下,它將在「 PAID / READY?」中寫FALSE。列,然後餐廳將需要更新該列。

在最後階段,腳本會將TRUE添加到「 CUSTOMER HERE?」 列,並在「提取信息」列中提供汽車說明。

5f28658a23ffb2.57184708.png

等待時間

這是一個非常簡單的標籤,因為它包含一個單元格,餐廳在該單元格中寫入要在準備好訂單之前需要多長時間。我們的代碼將提取該內容並將其提供給Twilio,讓客戶知道他們將等待多長時間。

5f28658ae01108.79987678.png

可用的菜肴和添加選項卡

餐館列出了現在可用的菜肴以及對這些菜肴的簡單修改,然後這些菜單在顧客聯繫餐館時發送給顧客。當代碼收到訂單時,它還將根據發送的菜肴列表檢查該訂單,以查看客戶是否選擇了其中一種。

5f28658b8d6c85.52430980.png5f28658c33be49.78717800.png

使用工作表標籤的腳本

您根本不需要觸摸它-這只是為了避免我們的代碼意外覆蓋自己。

想像一下這樣一種情況,我們的代碼獲取一個訂單,在訂單表中找到第一個空行,並將該訂單寫在此處。但是,與此同時,其他人為同一家餐廳下了訂單,我們代碼的另一個實例也尋找第一個空行,選擇了同一行,並且他們都在同一時間寫入了該行。即使代碼認為一切都很好,我們也會丟失至少一個訂單。

為了避免這種情況,當我們的代碼開始使用表格時,首先要做的是將「 Script using sheet」值更改為TRUE,並在開始使用表格時寫下來。然後,完成後,將值更改回FALSE。

如果我們的腳本使用該工作表,並且看到「使用工作表的腳本」設置為TRUE,它將等待該值變為FALSE,然後記下該順序。

5f28658cd1e277.89314716.png

如何使用床單?

餐廳表示例:

  1. 複製示例餐廳表。
  2. 填寫您的測試餐廳的所有詳細信息。
  3. 複製工作表的網址。

查找表:

  1. 製作一份查找表的副本(您只需創建一個)。
  2. 不要刪除「提取的ID」列中的任何內容,而要替換其他所有內容。
  3. 在第一欄中輸入您的Twilio號碼。
  4. 將測試餐廳的網址粘貼到「業務表網址」列中。
  5. 在最後一欄中添加您公司的電話號碼。

分享:

  1. 找到「服務帳戶」電子郵件地址(我將在「雲功能」部分中將您定向到該電子郵件地址)。
  2. 確保兩個工作表都與具有編輯許可權的電子郵件地址共享。

創建一個新餐廳:

  1. 任何時候您需要創建一個新餐廳時,只需複製餐廳表即可。
  2. 複製時,請確保勾選「與同一人共享」。
  3. 清除當前詳細信息。
  4. 將新的Google表格URL粘貼到查找表的新行中。

代碼運行時,它將打開查找表,使用Twilio電話號碼查找該餐廳的特定表ID,轉到該表,然後返回菜單。

Google Cloud功能

Google Cloud Functions是一種簡單的自動在線運行代碼的方法,而無需在特定位置設置伺服器或安裝一堆特殊程序來確保代碼可傳輸。

如果您不想了解有關Google Cloud的更多信息,而只想運行代碼,那麼這裡是免費的chatbot Python代碼

代碼在做什麼?

我們的代碼不會嘗試處理任何實際的對話,它只是從Twilio獲取請求-包括有關用戶及其所處階段的詳細信息-並執行一些簡單的功能。

階段1:「開始」

該代碼從Twilio接收一條消息,其中包括已激活的Twilio編號以及用戶所在的階段(開始)。基於它是「啟動」階段,該代碼激活了啟動功能。

它根據Twilio編號查找特定的餐廳表,然後返回該餐廳的菜單。

它還發送Twilio之類的信息,例如特定餐廳的編號,菜單的精簡版本以及我們可以用來檢查訂單的其他內容。

第二階段:「選擇」

該代碼接收用戶(選擇)所處的階段以及他們的訂購消息,餐廳的工作表ID和壓縮菜單(之前已發送給Twilio),因此我們不必查找這些內容再次。

基於它是「選擇」階段,該代碼將激活所選功能。它檢查訂單是否與我們的精簡菜單匹配。如果沒有,它將告訴Twilio該消息看起來不像命令。 

如果訂單與我們的菜單匹配,它將在第一行空白處寫下訂單。它還會創建一個訂單ID,該ID是時間和一部分用戶電話號碼的組合。

它會向Twilio發送一條消息,說明訂單是否與我們的菜單匹配,如果訂單與我們的菜單匹配,則訂單號是什麼。

第三階段:「到達」

該代碼接收用戶到達(到達)的階段並激活到達的功能。它還會接收到描述用戶的車輛,餐廳特定的工作表ID和訂單號的消息,這些消息先前已告知Twilio。

它查找餐廳表,並找到與其發送的訂單相匹配的訂單ID,然後更新該行以顯示用戶已經到達並描述他們的汽車。

Twilio處理所有上下文

您似乎很奇怪,每當代碼找到一些信息(例如,要查找的工作表ID)時,它就會將該信息發送給Twilio,並在以後再次請求它。那是因為除了Twilio告訴我們的內容外,我們的代碼根本不知道發生了什麼。每次我們激活代碼時,它的啟動方式都完全相同,因此它無法知道哪個用戶正在向Twilio發簡訊,他們處於什麼階段,甚至我們正在談論的餐廳。

Twilio在交互過程中會記住這些東西,因此我們使用它來處理所有這些東西。我們的代碼是一個非常簡單的「執行程序」-一次不知道任何內容的時間超過五秒鐘。

如何設置代碼?

我沒有時間描述如何深入使用Google Cloud Functions或如何使用Python進行編碼,但是我在上面共享的代碼中包含大量注釋,可以解釋發生了什麼,我將與您談談通過此過程的特定步驟。

步驟1:設定

確保你:

步驟2:建立新功能

轉到此處,然後單擊「創建新功能」。如果您以前從未創建過項目,則可能需要先執行該操作,然後再為該項目命名。

5f28658d8f3472.55862613.png

步驟3:列出您的功能的詳細信息

下面的屏幕快照為您提供了許多所需的詳細信息。我建議您選擇256MB的內存-應該足夠了。如果發現問題(或者從一開始就更加謹慎),則將其增加到512MB。

5f286590ef3968-139109.jpg

確保選擇HTTP作為觸發器,並記下它提供的URL(如果您忘記了,可以隨時通過轉到函數的「 Trigger」選項卡找到URL)。

還要確保您選中允許未經身份驗證的訪問的選項(這樣Twilio將能夠啟動該功能)。

選擇「內聯編輯器」,然後粘貼我給您的Gist代碼(對此進行了大量評論,我建議您對其進行閱讀,以確保您對它的工作感到滿意)。

點擊「 REQUIREMENTS.TXT」,然後粘貼您需要使用的以下庫:

  • 燒瓶
  • 特威里奧
  • pytz

確保「要執行的功能」是SMS,然後單擊「環境變數」下拉列表。

就像我在上面所做的那樣,單擊「 +添加變數」,在「名稱」列中輸入「 spreadsheet_id」,然後在「值」列中,粘貼您的查找表的ID。通過查看查找表的URL,然後複製最後兩個斜杠之間的所有內容(下面用紅色概述),可以獲取ID。

5f28658f053451-12973.jpg

點擊「服務帳戶」下拉菜單。它應該僅帶有「 App Engine默認服務帳戶」,並為您提供一個電子郵件地址(如下所示),這是您需要與所有Google表格共享的電子郵件地址。將其寫下來,然後將其添加為查找表和餐廳特定表的編輯用戶。

5f28658f9dd235.88532110.png5f286590635b46.13167057.png

完成所有這些操作後,單擊「部署」。

部署後,您應該回到雲功能的主屏幕。左上角的綠色對勾表示您一切正常。

步驟4:開啟Sheets API
5f28659282fda7-59952.jpg

您的代碼首次嘗試訪問Google表格時,由於您需要打開帳戶的Google表格API,因此可能無法訪問。轉到此處,使用左上角的下拉菜單選擇您正在處理的項目,然後單擊藍色的大「啟用」按鈕。

步驟5:返回Twilio並為代碼粘貼HTTP觸發器

還記得我們創建函數時記下的觸發器URL嗎?返回您的Twilio Studio並找到左上角帶有</>符號的所有塊:

5f2865931a22f6.74509200.png

依次單擊每個,然後將您的Google Cloud URL粘貼到屏幕右側出現的REQUEST URL框中:

5f286593b38e50.42446384.png測試機器人

現在,您應該已經設置了Cloud Function。您還應該同時設置兩個Google表格並與您的Cloud Function服務帳戶共享。

下一步是測試機器人。首先給Twilio數字發簡訊「 order」一詞,以使其正常運行。它應該以菜單進行響應,您的代碼將從您的餐廳特定的Google表格中提取。請遵循將其發送到最後的步驟,並檢查您的Google表格,以確保其正確更新。

如果由於某種原因它不起作用,可以在兩個地方檢查。通過單擊右上角的小「 Debugger」符號,Twilio保留了所看到的所有錯誤的日誌:

5f2865945483a4.95845406.png

Google還會記錄您的Cloud Function發生的所有情況。這包括非錯誤通知。您可以通過單擊頂部的「查看日誌」來查看所有這些信息:

5f286594f22173.27811194.png結論:打破事物,玩得開心

所有這些都不是完美的,而且我敢肯定您可以添加和改進,但是這是一種構建可伸縮聊天機器人網路的方式,每個聊天機器人都專門針對不同的業務,並且由該業務部分管理最低成本。

試試看,破壞它,改進它,撕毀它,然後重新開始,讓我知道您的想法!

 

後記:怪異的駭客

這一點只對有興趣的人真正有用,但是由於我們故意在小範圍內完成此操作,因此我們遇到了一些奇怪的問題-主要是關於尚未被激活的對我們的機器人的請求。

當Twilio在一段時間內第一次收到消息時,它會很快打開,並期望其他事情也會這樣做。例如,當Twilio向我們的代碼發出請求時,它假定代碼花費的時間超過大約五秒鐘,則該代碼失敗。這不是很不尋常-許多聊天平台要求最長五秒鐘的周轉時間。

即使使用較低的內存餘量,Cloud Functions都可以運行得非常快,但是通過API訪問Google表格似乎總是有點慢。實際上,如果一段時間未訪問Google表格,則它的速度特別慢。

這意味著,如果最近沒有人使用您的漫遊器,則Google Sheets API花費的時間太長,無法在第一時間做出響應,而Twilio在我們的代碼返回之前就放棄了,從而導致錯誤。

我們的腳本中有兩部分旨在避免這種情況。

再試一次

第一次激活雲功能時,我們不希望它實際更改任何內容,而只需要信息。因此,在Twilio中,我們首先創建一個名為「 retries」的變數並將其值設置為0。 

如果請求失敗,則檢查重試值是否為0。如果是,則將重試值設置為1,然後重試。如果第二次失敗,我們不想永遠這樣做,因此我們會發送錯誤並在那裡停止。

喚醒床單

第二次激活雲功能時,我們確實希望它做某事。如果沒有及時返回,我們就不能再做一次,因為我們最終將獲得重複的訂單,這對於餐廳來說是一個頭疼的問題。

取而代之的是,在交換的較早部分中,我們對一張工作表進行了無意義的更改,以便在進行重要更改時可以隨時進行準備。

在對話流程中,我們:

  1. 發送菜單
  2. 得到回應
  3. 詢問用戶名
  4. 寫訂單

在第四步之前,我們不需要對錶單做任何事情,但是在得到用戶的響應之後(在詢問他們的姓名之前),我們將激活代碼一次,以將無用的東西寫入訂單中。我們對Twilio說(無論是成功還是失敗)繼續進行互動,因為在那個時候我們是否及時返回都無關緊要。然後,希望在我們按訂單編寫時,Google表格已經可以實際使用了。

有局限性

Google表格不是理想的資料庫-它運行緩慢,可能意味著我們錯過了Twilio的超時。但是,這幾個額外的步驟可幫助我們解決其中一些限制。

Total
0
Shares
相關文章