6
8

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Gin(Golan)製で作った今話題のLINE BOT APIをHeroku上で動かしてみた!

Last updated at Posted at 2016-04-10

LINE BOT API Trial Accountが、10,000名まで先行申し込み受付中!とあったので、公開直後にアカウント作って、遊んでみた

とりあえずよくあるオウムさんを作りました。

使った物

  • Golang
  • Gin
  • Heroku
  • Fixie(Heroku Addon)

cmd/go-getting-started/main.go

package main

import (
	"bytes"
	"encoding/json"
	"fmt"
	"log"
	"net/http"
	"net/url"
	"os"
	"time"

	"github.com/gin-gonic/gin"
)

//BotRequestBody リクエスト内容を格納
type BotRequestBody struct {
	Request BotRequest `json:"Request"`
}

//BotRequest
type BotRequest struct {
	Result []BotResult `json:"result"`
}

type BotResult struct {
	From        string   `json:"from"`
	FromChannel string   `json:"fromChannel"`
	To          []string `json:"to"`
	ToChannel   string   `json:"toChannel"`
	EventType   string   `json:"eventType"`
	ID          string   `json:"id"`
	Content     Content  `json:"content"`
}

type Content struct {
	ID          string   `json:"id"`
	ContentType int      `json:"contentType"`
	From        string   `json:"from"`
	CreatedTime int      `json:"createdTime"`
	To          []string `json:"to"`
	ToType      int      `json:"toType"`
	Text        string   `json:"text"`
}

type SendRequest struct {
	To        []string `json:"to"`
	ToChannel int      `json:"toChannel"`
	EventType string   `json:"eventType"`
	Content   Content  `json:"content"`
}

const (
	EndPoint  = "https://trialbot-api.line.me/v1/events"
	ToChannel = 1383378250
	EventType = "138311608800106203"
)

func main() {
	router := gin.New()
	router.Use(gin.Logger())
	router.POST("/linebot/callback", callbackHandler)
	router.Run(":" + os.Getenv("PORT"))
}

func callbackHandler(c *gin.Context) {
	var botRequest BotRequest
	if c.Bind(&botRequest) == nil {
		c.JSON(http.StatusOK, gin.H{"status": fmt.Sprintf("request convert error, request data is %+v", botRequest)})
		return
	}

	for _, result := range botRequest.Result {

		request := SendRequest{
			To:        []string{result.Content.From},
			ToChannel: ToChannel,
			EventType: EventType,
			Content: Content{
				ContentType: result.Content.ContentType,
				ToType:      result.Content.ToType,
				Text:        result.Content.Text,
			},
		}

		if _, err := post(request); err != nil {
			log.Printf("Error: %s", err.Error())
		}
	}

	c.JSON(http.StatusOK, gin.H{"status": "end"})
}

func post(r SendRequest) (*http.Response, error) {
	b, _ := json.Marshal(r)
	req, _ := http.NewRequest(
		"POST",
		EndPoint,
		bytes.NewBuffer(b),
	)

	req = setHeader(req)

	proxyURL, _ := url.Parse(os.Getenv("FIXIE_URL"))
	client := &http.Client{
		Timeout:   time.Duration(15 * time.Second),
		Transport: &http.Transport{Proxy: http.ProxyURL(proxyURL)},
	}

	return client.Do(req)
}

func setHeader(req *http.Request) *http.Request {
	req.Header.Add("Content-Type", "application/json; charset=UTF-8")
	req.Header.Add("X-Line-ChannelID", os.Getenv("LINE_CHANNEL_ID"))
	req.Header.Add("X-Line-ChannelSecret", os.Getenv("LINE_CHANNEL_SECRET"))
	req.Header.Add("X-Line-Trusted-User-With-ACL", os.Getenv("LINE_CHANNEL_MID"))
	return req
}

line bot.gif
oli2310i.png

6
8
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
6
8

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?