IT/AI

Dialogflow - 5. Webhook

루벤초이 2021. 4. 19. 19:18

Dialogflow 웹앱 시리즈입니다.

★Sample Code


지난 시간에 fulfillment inline editor를 사용해서 외부 사이트 연동해 봤습니다.

 

서비스가 복잡해지면 fulfillment 코드도 복잡해지는만큼, webhook이 필수적인데요, 지금부터는 fulfillment inline editor 대신, webhook을 사용해서 더 확장해 보겠습니다. 우리가 개발하려는 시스템 구조는 아래와 같습니다.

 

시스템 구조

이 전체 구조 중 클라이언트는 Try it now로 대체하고 3rd party 예약 시스템은 Cloud Functions RESTful API로 구현해봅시다.

오늘 구현할 범위

 

Firebase Cloud Functions

우리는 fulfillment용 cloud functions와 (3rd party 예약 시스템에 해당하는) RESTful API용 cloud functions이 필요합니다. RESTful API란 간단히 말하자면 웹 서버로 정보/액션을 요청하고 응답/결과를 받는 인터페이스입니다.

 

전자는 지난 시간에 만든 newagent-tdyh를 사용하고 후자는 새로 rubenchoi-test라는 GCP 프로젝트를 만든 다음 firebase 콘솔에서 rubenchoi-test를 추가합니다. 관련 내용은 Google Cloud Platform & Firebase 편을 참고하세요.

 

3rd Party 예약 시스템 - RESTful API Cloud Functions

먼저 RESTful API cloud functions를 만들어봅시다. RESTful API를 만들기 위해 rubenchoi-test/functions로 가서 express를 설치합니다.

  • npm install express --save

express는 웹 프레임워크로 쉽고 빠르게 웹 서버를 만들 수 있습니다.이제 rubenchoi-test/functions/index.js를 아래와 같이 수정합니다.

const functions = require("firebase-functions");

const app = require('express')();
app.get('/test/', (req, resp) => {
    resp.json({ type: 'test', data: 'Testdata' });
});

const api = functions.https.onRequest(app);

module.exports = {
    api
}

firebase deploy 해주면 아래와 같이 로그가 나타나는데,

Function URL (api)라고 나온 부분을 복사해서 브라우저에서 열어봅니다. 즉, us-central1-rubenchoi-test.cloudfunctions.net/api/test를 열면,

index.js에서 정의했던 JSON 응답이 리턴됩니다. 그런데 URL이 좀 복잡하네요? 맨 마지막 줄에 있는 깔끔한 Hosting URL을 사용할 수는 없을까요? rubenchoi-test/firebase.json을 열고 아래와 같이 hosting에 rewrites를 추가합니다.

{
  "hosting": {
    "public": "public",
    "ignore": [
      "firebase.json",
      "**/.*",
      "**/node_modules/**"
    ],
    "rewrites": [
      {
        "source":"/**",
        "function": "api"
      }
    ]
  }
}

이것은 hosting URL로 들어오는 모든 GET method를 api function으로 돌리겠다는 의미입니다. 즉, rubenchoi-test.web.app/test를 입력하면 같은 JSON 응답이 나옵니다. 뭐, 너무나 당연한 얘기지만, 만일 이 상태에서 fulfillment inline editor의 weatherAPI()의 URL을 아래와 같이 rubenchoi-test URL로 변경하면 샘플 서버 대신 우리 서버와 통신하겠죠.

  function weatherAPI() {
      const url = "https://rubenchoi-test.web.app/test";
      return new Promise((resolve, reject) => {
          https.get(url, function (res) {
              console.log("**************************");
              console.log(res.statusCode, res.headers);
              var json = "";
              res.on("data", function (chunk) {
                  console.log("received JSON response: " + chunk);
                  json += chunk;
              });

              res.on("end", function () {
                  let jsonData = JSON.parse(json);
                  let r = "Type: " + jsonData.type + " Data: " + jsonData.data;
                  resolve(r);
              });
          });
      });
  }

우리 서버와 연동 검증

이해되셨나요? 이제 우리의 다음 목표인 fulfillment inline editor → webhook으로 대체해 보겠습니다.

 

Fulfillment to Webhook

우선 newagent-tdyh/functions로 가서 dialogflow 라이브러리를 설치합니다.

  • npm  install  --save dialogflow  dialogflow-fulfillment  actions-on-google

이제 브라우저로 Dialogflow 콘솔로 가서 Inline Editor의 내용을 그대로 복사해서 newagent-tdyh/functions/index.js에 붙여넣고 배포합니다.

  • firebase deploy

브라우저를 열어 Dialogflow 콘솔로 가서 Webhook을 enable 해주고 (Inline Editor는 자동으로 비활성화됩니다.) URL에 Function URL을 넣어줍니다. (디폴토 값으로 이미 설정된 경우도 있습니다.)

제대로 바뀌었는지 확인하기 위해 weatherAPI() 응답 메시지 앞에 'From Webhook and 3rd party' 문구를 추가했습니다.

 

결과를 봅시다.

와우! 우리가 원하던 응답이 나왔네요. 정리해 보면, 두 개의 firebase cloud functions을 만들어 그 중 하나를 기존의 fulfillment inline editor 대신 webhook으로 설정하고 다른 하나를 3rd party 시스템으로 구현하여 연동해 보았습니다.

 

이렇게 확장하면 어떤 외부 시스템이든 연동할 수 있겠지요. 다음 시간에는 RESTful API 대신 MQTT 프로토콜을 연결해보고 cloud functions 외에 일반적인 서버와도 연동해 보면서 Fulfillment/Webhook을 마무리하겠습니다.

오늘 구현한 범위

 

확장 설계

MQTT로 실시간 최신 정보 업데이트

가령 항상 최신 데이터를 유지하기 위해 3rd party 서버에 MQTT로 실시간 정보를 업데이트합니다.

Cloud function 외 퍼블릭 서버 사용

3rd party 서비스 부분은 Cloud functions 대신 public 서버로 대체하는 방법에는 크게 다음과 같은 것들이 있습니다.

  1. AWS EC2 같은 유료 클라우드 컴퓨트 서비스를 이용해 public IP를 얻는 방법
  2. 사설 망에서 AP 설정을 통해 pubilc ip를 얻는 방법
  3. 오픈소스 localtunnel을 통해 일시적으로 public ip를 얻는 방법

이 중 3번 localtunnel은 개발/테스트 용으로 아주 편리한데요, 단순히 설치 후 실행하면 인터넷으로 접속 가능한 도메인을 무료로 만들어 줍니다. 필요하신 분은 꼭 해보세요.

 

728x90
반응형