•  


WhatsApp Flows를 使用하여 豫約 進行하기: Node.js 백엔드 만들기
開發者 消息으로 돌아가기

WhatsApp Flows를 使用하여 豫約 進行하기: Node.js 백엔드 만들기

2024年 2月 27日 製作: 개피 G(Gafi G), 이리나 바그너(Iryna Wagner)

WhatsApp Flows를 使用하면 使用者가 WhatsApp에서 곧바로 作業을 完了하도록 支援하는 인터랙티브 메시지를 만들 수 있습니다. 플로를 使用하여 使用者 相互 作用을 위한 畵面을 만들 수 있습니다. 例를 들어, 潛在 顧客 情報 蒐集이나 리뷰 提出을 위한 簡單한 入力 樣式을 만들 수 있습니다. 여러 畵面에 걸친 複雜한 豫約 進行 플로를 設計할 수도 있습니다.

이 가이드에서는 使用者가 WhatsApp Flows를 통해 豫約을 進行하도록 支援하는 Node.js 앱을 만드는 方法을 段階別로 案內합니다. 먼저 WhatsApp Business 플랫폼에서 플로를 만든 다음, 플로의 應答을 受信하고 豫約을 進行하는 Webhook을 構成합니다.

必須 條件

튜토리얼을 따라서 進行하려면 다음이 必要합니다.

WhatsApp 플로 만들기

WhatsApp 플로는 플로 빌드 道具 UI(WhatsApp 管理者를 통해 액세스) 또는 플로 API를 使用하여 만들 수 있습니다. 이 튜토리얼에서는 플로 빌드 道具를 使用합니다.

플로 만들기

WhatsApp 管理者 대시보드 왼쪽 메뉴에서 計定 道具 를 選擇합니다. 그런 다음 Flows 를 클릭합니다.

WhatsApp 관리자 그래픽

오른쪽 上段에서 플로 만들기 를 클릭합니다.

플로 만들기 그래픽

標示되는 對話 箱子에서 豫約 플로의 詳細 情報를 入力합니다.

  • 이름 ? BookAppointment 또는 願하는 이름을 入力합니다.
  • 카테고리 ? 豫約 을 選擇합니다.
  • 템플릿 ? 豫約하기 를 選擇합니다. 이 템플릿에는 豫約 進行을 위한 必須 要素가 包含되어 있습니다. 이러한 必須 要素에는 豫約 詳細 情報 畵面, 使用者 詳細 情報 入力 畵面, 豫約 要約 畵面, 會社 約款 標示 畵面 等이 있습니다. 使用 事例에 맞게 템플릿을 追加로 맞춤 設定할 수 있습니다.
예약하기 그래픽

提出 을 클릭하여 플로를 만듭니다.

빌드 道具 UI의 오른쪽에서 플로를 미리 볼 수 있습니다. 豫約 畵面에서는 使用者가 位置, 날짜와 같은 豫約 詳細 情報를 選擇할 수 있습니다. 詳細 情報 畵面에서는 使用者가 情報를 入力합니다. 要約 畵面에는 豫約 要約이 標示됩니다. 마지막 畵面에는 會社 弱冠이 標示됩니다.

플로를 修正하는 中에는 플로가 臨時 貯藏本 狀態로 維持됩니다. 플로는 現在 테스트 用途로 팀 內에서만 共有할 수 있습니다. 플로를 다른 公開 對象에게 共有하려면 揭示해야 합니다. 單, 揭示한 플로는 修正할 수 없습니다. 이 豫約 플로에는 아직 엔드포인트 URL을 追加해야 하므로 臨時 貯藏本 狀態로 남겨두고 엔드포인트를 構成하는 다음 段階로 넘어가겠습니다.

플로의 엔드포인트 構成하기

WhatsApp Flows에서는 外部 엔드포인트에 連結할 수 있습니다. 이 엔드포인트는 플로를 위한 動的 데이터를 提供하며 經路를 制御합니다. 또한 플로로부터 使用者가 提出한 應答을 受信합니다.

이 가이드에서는 테스트 用途로 Glitch를 使用하여 엔드포인트를 호스팅합니다. Glitch를 使用하는 것은 全的으로 選擇 事項이며, Flows를 使用하기 위한 必須 事項이 아닙니다. GitHub의 엔드포인트 코드를 複製 하여 願하는 環境에서 實行할 수 있습니다.

Glitch의 엔드포인트 코드 에 액세스한 다음 이를 리믹스하여 固有한 도메인을 가져옵니다. 리믹스하려면 페이지 上段에서 리믹스 를 클릭합니다. Glitch 페이지 오른쪽의 入力 要素에 固有한 도메인이 자리 標示子로 標示됩니다.

다음으로 넘어가기 前에 코드를 살펴보겠습니다. src 디렉토리에는 4個의 JavaScript 파일이 있습니다( encryption.js , flow.js , keyGenerator.js , server.js ). 첫 番째 進入點 파일인 server.js 부터 살펴보겠습니다.

server.js

server.js 파일은 먼저 Express 애플리케이션이 express.json 미들웨어를 使用하여 受信 JSON 要請을 構文 分析하도록 構成합니다. 그런 다음 엔드포인트에 必要한 環境 變數를 읽어들입니다.

const { APP_SECRET, PRIVATE_KEY, PASSPHRASE, PORT = "3000" } = process.env;

APP_SECRET 은 署名 認證에서 使用됩니다. 메시지가 WhatsApp을 통해 受信된 것인지, 卽 處理하기에 安全한 것인지 檢査합니다. APP_SECRET은 .env 파일에 追加합니다.

APP_SECRET 에 액세스하려면 Meta for Developers의 앱 대시보드로 移動합니다. 왼쪽 探索 메뉴의 앱 설정 아래에서 基本 을 選擇합니다. 앱 시크릿 아래에서 標示 를 클릭하고 시크릿을 複寫합니다. 그런 다음 Glitch로 돌아가서 .env 파일을 열고 方今 複寫한 시크릿의 값을 使用하여 變數 APP_SECRET 을 만듭니다.

PRIVATE_KEY 는 受信된 메시지를 解毒합니다. PASSPHRASE 는 非公開 키를 認證하는 데 使用됩니다. 非公開 키를 使用할 때는 여기에 對應되는 公開 키가 必要합니다. 公開 키는 뒷部分에서 업로드할 것입니다. 여기서는 프로덕션 計定에서 使用하는 非公開 키를 使用하지 마세요. Glitch에서의 테스트를 위한 臨時 非公開 키를 만들어서 비즈니스 인프라에서 프로덕션 키 代身 使用하세요.

Glitch 터미널에서 아래 命令을 實行하여 公開-非公開 키 雙을 生成합니다. <your-passphrase> 를 指定된 祕密 文句(passphrase)로 바꿉니다. 페이지 下端에서 터미널 탭을 클릭하여 Glitch 터미널에 액세스합니다.

node src/keyGenerator.js <your-passphrase>

祕密 文句와 非公開 키를 複寫하여 .env 파일에 붙여넣습니다. 왼쪽 사이드바에서 .env 파일을 클릭한 다음 上段의 ?? 一般 텍스트 를 클릭합니다. UI에서 곧바로 修正하면 키 棲息이 變更되니 注意하세요.

環境 變數를 設定한 後에는 앞에서 生成한 公開 키를 複寫하여 그래프 API를 통해 公開 키를 업로드 합니다.

server.js 파일에는 다음과 같은 여러 段階를 遂行하는 POST 엔드포인트도 들어 있습니다.

  • 非公開 키가 있는지 確認합니다.
       if (!PRIVATE_KEY) { throw new Error('Private key is empty. Please check your env variable "PRIVATE_KEY".'); }
  • 파일 下段에 있는 isRequestSignatureValid 函數를 使用하여 要請 署名을 檢證합니다.
if(!isRequestSignatureValid(req)) { // Return status code 432 if request signature does not match. // To learn more about return error codes visit: https://developers.facebook.com/docs/whatsapp/flows/reference/error-codes#endpoint_error_codes return res.status(432).send(); }
  • encryption.js 파일의 decryptRequest 函數를 使用하여 受信 메시지를 解毒합니다.
      let decryptedRequest = null; try { decryptedRequest = decryptRequest(req.body, PRIVATE_KEY, PASSPHRASE); } catch (err) { console.error(err); if (err instanceof FlowEndpointException) { return res.status(err.statusCode).send(); } return res.status(500).send(); } const { aesKeyBuffer, initialVectorBuffer, decryptedBody } = decryptedRequest; console.log("?? Decrypted Request:", decryptedBody);
  • 使用者에게 表示할 플로 畵面을 定합니다. getNextScreen 函數는 뒤에서 仔細히 살펴볼 것입니다.

const screenResponse = await getNextScreen(decryptedBody);

       console.log("?? Response to Encrypt:", screenResponse);
  • 使用者에게 電送할 應答을 暗號化합니다.
res.send(encryptResponse(screenResponse, aesKeyBuffer, initialVectorBuffer));

encryption.js

이 파일에는 保安을 위해 交換되는 메시지를 暗號化하고 解讀하는 老職이 들어 있습니다. 이 튜토리얼에서는 이 파일의 內容을 살펴보지 않습니다.

keyGenerator.js

이 파일은 앞에서 본 것처럼 非公開 키와 公開 키를 生成합니다. 이 튜토리얼에서는 encryption.js 파일과 마찬가지로 keyGenerator.js 파일의 內容을 살펴보지 않습니다.

flow.js

이 파일에는 플로 處理 老職이 들어 있습니다. 이 파일은 이름이 SCREEN_RESPONSES 人 個體로 始作합니다. 個體에는 畵面 ID와 各各의 詳細 情報(예: 데이터 交換에 使用되는 基本 設定 데이터)가 들어 있습니다. 이 個體는 플로 빌드 道具의 "..." > 엔드포인트 > 조각 > 應答 에서 生成됩니다. 이 個體에는 플로가 成功的으로 完了되면 클라이언트 機器로 電送되는 ID인 SUCCESS 도 들어 있습니다. SUCCESS가 電送되면 플로가 닫힙니다.

getNextScreen 函數에는 使用者에게 表示할 플로 데이터를 엔드포인트에 알려주는 老職이 들어 있습니다. 이 函數는 解讀된 메시지에서 必須 데이터를 抽出하는 것으로 始作합니다.

const { screen, data, version, action, flow_token } = decryptedBody;

WhatsApp Flows 엔드포인트는 一般的으로 다음과 같은 3가지 要請을 受信합니다.

各 要請의 詳細 情報는 엔드포인트 文書 를 參照하세요.

이 函數는 아래 코드에 나와 있는 것처럼 if 門을 使用하여 狀態 點檢과 誤謬 알림을 處理하고 그 結果에 따라 應答합니다.

// handle health check request if (action === "ping") { return { version, data: { status: "active", }, }; } // handle error notification if (data?.error) { console.warn("Received client error:", data); return { version, data: { acknowledged: true, }, }; }
        

使用者가 플로의 行動 誘導(CTA) 버튼을 클릭하면 INIT 액션이 트리거됩니다. 이 액션은 豫約 畵面과 데이터를 返還합니다. 또한 使用者가 모든 필드를 入力할 수 있도록 位置, 날짜, 時間 드롭다운을 비활성화합니다.

例를 들어, 날짜 드롭다운은 位置 드롭다運이 作成된 境遇에만 活性化됩니다. 필드의 活性化 및 非活性化는 data_exchange 要請이 受信된 境遇에 處理됩니다.

// handle initial request when opening the flow and display APPOINTMENT screen if (action === "INIT") { return { ...SCREEN_RESPONSES.APPOINTMENT, data: { ...SCREEN_RESPONSES.APPOINTMENT.data, // these fields are disabled initially. Each field is enabled when previous fields are selected is_location_enabled: false, is_date_enabled: false, is_time_enabled: false, }, }; }

data_exchange 액션의 境遇, switch case 門을 통해 畵面 ID에 따라 어떤 데이터를 電送할지 定해집니다. 畵面 ID가 APPOINTMENT 이면 앞에 나온 드롭다運이 모두 選擇된 境遇에만 드롭다운 필드가 活性化됩니다.

// Each field is enabled only when previous fields are selected is_location_enabled: Boolean(data.department), is_date_enabled: Boolean(data.department) && Boolean(data.location), is_time_enabled: Boolean(data.department) && Boolean(data.location) && Boolean(data.date)

DETAILS 畵面의 境遇, SCREEN_RESPONSES.APPOINTMENT.data 個體에서 데이터 個體 屬性의 題目(위치, 部署 等)李 抽出됩니다. 이 코드는 有效한 매칭이 存在한다고 假定하기 때문에 매칭되는 個體가 없는 境遇 誤謬가 發生할 수 있습니다.

이제 位置 個體 인스턴스를 살펴보겠습니다. 特定 位置 個體의 選擇 與否는 配列에 들어 있는 個體의 id 屬性을 data.location 의 값에 매칭하여 定해집니다.

const departmentName = SCREEN_RESPONSES.APPOINTMENT.data.department.find( (dept) => dept.id === data.department ).title; const locationName = SCREEN_RESPONSES.APPOINTMENT.data.location.find( (loc) => loc.id === data.location ).title; const dateName = SCREEN_RESPONSES.APPOINTMENT.data.date.find( (date) => date.id === data.date

).title;

그런 다음 값이 連結되고 應答으로 返還되어 SUMMARY 畵面이 렌더링됩니다.

const appointment = `${departmentName} at ${locationName} ${dateName} at ${data.time}`; const details = `Name: ${data.name} Email: ${data.email} Phone: ${data.phone} "${data.more_details}"`; return { ...SCREEN_RESPONSES.SUMMARY, data: { appointment, details, // return the same fields sent from client back to submit in the next step ...data, }, };
        

클라이언트에서 SUMMARY 畵面이 提出되면 클라이언트 機器로 SUCCESS 應答이 電送되어 플로가 完了로 標示됩니다. flow_token 은 使用者에게 플로를 電送할 때 設定할 수 있는 固有한 識別者입니다.

// send success response to complete and close the flow return { ...SCREEN_RESPONSES.SUCCESS, data: { extension_message_response: { params: { flow_token, }, }, }, };

TERMS 畵面에는 交換해야 하는 데이터가 없으므로 이 畵面은 엔드포인트가 處理하지 않습니다.

플로에 엔드포인트 追加하기

Glitch 페이지 上段에서 kebab 메뉴 아이콘을 클릭하고 링크 複寫 를 選擇하여 URL을 複寫할 수 있습니다. 오른쪽 上段에서 共有 를 클릭하여 링크를 가져올 수도 있습니다.

플로 에디터로 移動합니다. 에디터 上段에 標示되는 褐色 배너에서 설정 을 클릭합니다.

엔드포인트 URI, 비즈니스 電話番號, Meta for Developers의 앱을 構成할 수 있는 팝업이 標示됩니다. 必須 構成을 適用한 後에는 狀態 點檢을 遂行합니다. 먼저 인터랙티브 미리 보기를 實行하고 인터랙티브 미리 보기 設定의 첫 番째 畵面에서 데이터 要請 아래에서 데이터 要請 을 選擇합니다. 이렇게 하면 엔드포인트를 使用할 수 있고 狀態 點檢이 具現되었는지 檢證한 後 첫 番째 畵面의 데이터를 가져오는 要請이 엔드포인트로 電送됩니다.

그런 다음 미트볼( ... ) 메뉴를 클릭하고 揭示 를 選擇하여 플로를 揭示합니다. 이렇게 하면 揭示에 앞서 엔드포인트를 檢證하기 위해 action === "ping" 과 함께 狀態 點檢 要請이 엔드포인트로 電送됩니다.

엔드포인트 그래프

플로 테스트하기

構成을 完了한 後에는 WhatsApp 빌드 道具 UI에서 다시 한番 인터랙티브 미리 보기를 토글하여 플로를 테스트합니다. 標示되는 팝업에서 電話番號를 選擇하고 첫 番째 畵面에서 데이터 要請 아래에서 데이터 要請 을 選擇합니다. X 아이콘을 클릭하여 플로를 닫으면 CTA 버튼을 使用하여 플로 테스트를 새로 始作할 수 있습니다.

로그 탭을 클릭하여 Glitch 로그를 엽니다. 지우기 를 클릭하여 로그를 지웁니다. 그런 다음 WhatsApp 빌드 道具 UI 미리 보기로 돌아갑니다. 플로 미리 보기 를 클릭합니다. 다음과 같은 畵面을 볼 수 있습니다.

플로 미리 보기 그래픽

이제 Glitch 로그로 돌아갑니다. Decrypted Request 아래에서 INIT 액션, 플로 토큰 및 其他 詳細 情報를 볼 수 있습니다. 部署 드롭다運이 選擇되면 使用者 플로로 電送되는 Response to Encrypt도 볼 수 있습니다.

해독된 요청 그래픽

部署를 選擇합니다. 그러면 is_location_enabled true 로 設定되고 액션이 data_exchange 로 變更되는 것을 볼 수 있습니다.

데이터 교환 그래픽

繼續해서 플로를 使用해보며 Glitch 로그에서 데이터가 바뀌는 것을 살펴봅니다. 使用者가 모바일 機器에서 플로와 相互 作用할 때도 이와 비슷한 로그가 生成됩니다.

다음 섹션에서는 使用者가 豫約을 進行하면 使用者에게 確認 메시지를 電送하는 Webhook을 만들어봅니다.

Webhook 設定하기

使用者가 플로를 完了하면 플로를 完了로 表示하는 메시지가 購讀된 Webhook으로 電送됩니다. 이 Webhook을 使用하여 使用者에게 채팅 메시지를 통해 豫約이 成功했음을 알립니다. 엔드포인트의 境遇와 마찬가지로 Glitch를 使用하여 테스트해보겠습니다. 여기 에서 코드와 리믹스를 確認할 수 있습니다.

Glitch를 使用하는 것은 全的으로 選擇 事項이며, Flows를 使用하기 위한 必須 事項이 아닙니다. GitHub의 엔드포인트 코드를 複製 하여 願하는 環境에서 實行할 수 있습니다.

環境 變數 設定하기

環境 變數를 設定하려면 Glitch에서 .env 파일을 엽니다. VERIFY_TOKEN 을 願하는 文字列로, FLOW_ID 를 플로우의 ID로, GRAPH_API_TOKEN 을 WhatsApp Business 計定의 액세스 토큰으로 設定합니다. 왼쪽 探索 메뉴의 WhatsApp 섹션 아래에서 API 설정 을 클릭하여 Meta for Developers의 앱 대시보드에서 액세스 토큰을 確認할 수 있습니다.

API 설정 그래픽

렌더링되는 페이지에서 臨時 액세스 토큰 카드 아래의 輻射 버튼을 클릭합니다. .env 파일에 키를 붙여넣습니다.

Meta 대시보드에서 Webhook 購讀하기

Meta for Developers 計定에서 왼쪽 探索 패널에 있는 WhatsApp 아래의 構成 메뉴를 클릭합니다.

구성 그래픽

Webhook 카드에서 修正 을 클릭합니다. 標示되는 對話 箱子의 콜백 URL 필드에 複寫한 Glitch URL을 붙여넣고 그 뒤에 /webhook 을 追加합니다. 確認 토큰 필드에 .env 파일의 VERIFY_TOKEN 變數에서 確認한 토큰을 追加합니다. 作業을 마쳤으면 確認 및 貯藏 을 클릭합니다. 對話 箱子가 닫히고 基本 畵面이 標示됩니다. 管理 를 클릭하고 메시지 필드를 選擇합니다. 이제 Webhook이 準備되었습니다.

Webhook 코드 살펴보기

이 코드에는 POST /webhook GET /webhook , 이렇게 2個의 經路가 있습니다. GET 經路는 提供된 토큰을 미리 定義된 確認 토큰과 比較 檢査하고 適切한 狀態 코드와 質問 토큰으로 應答함으로써 Webhook 確認 要請을 處理합니다.

const verify_token = process.env.VERIFY_TOKEN; // Parse params from the webhook verification request let mode = req.query["hub.mode"]; let token = req.query["hub.verify_token"]; let challenge = req.query["hub.challenge"]; if (mode && token) { if (mode === "subscribe" && token === verify_token) { console.log("WEBHOOK_VERIFIED"); res.status(200).send(challenge); } else { res.sendStatus(403); } }

POST /webhook 經路는 受信 Webhook 알림을 處理합니다. Webhook 要請은 서로 다른 페이로드 를 가질 수 있습니다. 아래 코드는 값이 定義되지 않았을 境遇에 對備하여 要請 필드에 安全하게 액세스하여 메시지와 비즈니스 電話番號를 읽습니다.

const message = req.body.entry?.[0]?.changes[0]?.value?.messages?.[0]; const business_phone_number_id =

req.body.entry?.[0].changes?.[0].value?.metadata?.phone_number_id;

그런 다음 受信 要請이 'appointment'라는 單語를 包含하는 "text" 類型의 메시지에 對한 要請인지 檢査합니다. 메시지에 이 單語가 包含되어 있으면 使用者에게 플로가 電送됩니다. 플로 메시지는 flow_action: "data_exchange " 와 함께 電送됩니다. 卽, 플로는 實行되었을 때 엔드포인트에 INIT 要請을 電送하여 初期 畵面과 데이터를 가져옵니다.

if ( message.type === "text" && // for demo purposes, send the flow message whenever a user sends a message containing "appointment" message.text.body.toLowerCase().includes("appointment") ) { // send flow message as per the docs here https://developers.facebook.com/docs/whatsapp/flows/gettingstarted/sendingaflow#interactive-message-parameters await axios({ method: "POST", url: `https://graph.facebook.com/v18.0/${business_phone_number_id}/messages`, headers: { Authorization: `Bearer ${GRAPH_API_TOKEN}`, }, data: { messaging_product: "whatsapp", to: message.from, type: "interactive", interactive: { type: "flow", header: { type: "text", text: "Hello there ??", }, body: { text: "Ready to transform your space? Schedule a personalized consultation with our expert team!", }, footer: { text: "Click the button below to proceed", }, action: { name: "flow", parameters: { flow_id: FLOW_ID, flow_message_version: "3", // replace flow_token with a unique identifier for this flow message to track it in your endpoint & webhook flow_token: "<FLOW_TOKEN_PLACEHOLDER>", flow_cta: "Book an appointment", flow_action: "data_exchange", }, }, }, }, }); } ...

受信 메시지 類型이 "text" 가 아닌 境遇, 코드는 메시지 類型이 "interactive " 인지 檢査합니다. 인터랙티브 類型 "nfm_reply" 는 受信 메시지가 플로 應答임을 나타냅니다. 그런 다음 使用者에게 'You’ve successfully booked an appointment' 메시지를 電送합니다.

... if ( message.type === "interactive" && message.interactive?.type === "nfm_reply" ) { // send confirmation message await axios({ method: "POST", url: `https://graph.facebook.com/v18.0/${business_phone_number_id}/messages`, headers: { Authorization: `Bearer ${GRAPH_API_TOKEN}`, }, data: { messaging_product: "whatsapp", to: message.from, text: { body: "You've successfully booked an appointment" }, }, }); } ...

그런 다음 受信 메시지를 읽음으로 標示하여 使用者에게 파란色 체크 標示를 表示합니다.

... // mark incoming message as read await axios({ method: "POST", url: `https://graph.facebook.com/v18.0/${business_phone_number_id}/messages`, headers: { Authorization: `Bearer ${GRAPH_API_TOKEN}`, }, data: { messaging_product: "whatsapp", status: "read", message_id: message.id, }, }); ...
        

使用者 經驗

이 예제에서는 使用者가 비즈니스 電話番號로 'appointment'라는 單語가 包含된 메시지를 電送하고 플로 메시지를 受信합니다. 비즈니스는 다른 相互 作用이 이루어진 後에 또는 메시지 템플릿으로서 플로를 電送 할 수도 있습니다.

使用者는 豫約 進行을 위한 CTA 버튼이 包含된 플로 메시지를 受信하며, 여기에서 詳細 情報를 入力할 수 있습니다. 그런 다음 플로가 完了되면 確認 메시지를 受信합니다.

사용자에게 플로 전송하기 그래픽

이 가이드에서는 매끄러운 豫約 進行을 위한 WhatsApp 플로를 設定하는 方法을 알아보았습니다. 플로 빌드 道具 UI를 使用하여 使用者에게서 豫約 詳細 情報를 蒐集하는 樣式을 만들었습니다.

플로를 使用하면 豫約 進行을 위해 使用者를 外部 웹사이트로 리디렉션할 必要가 없기 때문에 使用者 經驗이 向上됩니다. 使用者는 簡單한 프로세스를 통해 WhatsApp에서 곧바로 豫約을 完了할 수 있습니다. WhatsApp Flows는 豫約 進行 外에도 顧客 서비스 피드백을 蒐集하거나 使用者가 프로모션 또는 메일링 리스트에 加入하도록 支援하는 用途로도 使用할 수 있습니다. WhatsApp Flows는 外部 API나 엔드포인트에 있는 다른 앱에 柔軟하게 連結됩니다.

플로 빌드 道具 UI를 使用하면 WhatsApp Flows를 손쉽게 만들 수 있습니다. 또한 플로 API를 使用하여 프로그래밍 方式으로 플로를 만들 수도 있습니다. 仔細한 內容은 WhatsApp Flows 文書 를 參照하세요.


- "漢字路" 한글한자자동변환 서비스는 교육부 고전문헌국역지원사업의 지원으로 구축되었습니다.
- "漢字路" 한글한자자동변환 서비스는 전통문화연구회 "울산대학교한국어처리연구실 옥철영(IT융합전공)교수팀"에서 개발한 한글한자자동변환기를 바탕하여 지속적으로 공동 연구 개발하고 있는 서비스입니다.
- 현재 고유명사(인명, 지명등)을 비롯한 여러 변환오류가 있으며 이를 해결하고자 많은 연구 개발을 진행하고자 하고 있습니다. 이를 인지하시고 다른 곳에서 인용시 한자 변환 결과를 한번 더 검토하시고 사용해 주시기 바랍니다.
- 변환오류 및 건의,문의사항은 juntong@juntong.or.kr로 메일로 보내주시면 감사하겠습니다. .
Copyright ⓒ 2020 By '전통문화연구회(傳統文化硏究會)' All Rights reserved.
 한국   대만   중국   일본