skill

package module
v2.0.2 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Mar 3, 2020 License: MIT Imports: 3 Imported by: 0

README

go-kakaoskill

  • golang카카오 i 오픈빌더 스킬 v2 라이브러리입니다.

  • 마땅한 라이브러리가 보이지 않아서 만들었습니다.

  • 카카오 i 오픈빌더 도움말 을 기반으로 제작하였습니다.

  • MIT license 하에 배포됩니다.

installation

  1. 먼저 Go (1.13 이상) 설치해주신 후, 다음 커맨드를 입력하여 go-kakaoskill 을 설치합니다.
$ go get -v "github.com/RyuaNerin/go-kakaoskill"
  1. 다음과 같이 import 하여 사용할 수 있습니다.
import skill "github.com/RyuaNerin/go-kakaoskill/v2" // go modules 사용 (GO111MODULE=on or $GOPATH 밖)
import skill "github.com/RyuaNerin/go-kakaoskill" // go modules 사용 안함

Quick start

  • skill.F skill.H 두 함수를 사용해서 http.HandlerFunc 로 변환해주세요.
// example.go
package main

import (
	"net/http"

	skill "github.com/RyuaNerin/go-kakaoskill/v2"
)

func main() {
	mux := http.NewServeMux()
	mux.HandleFunc("/simple1", skill.F(simpleFunc))
	mux.Handle("/simple2", skill.H(new(simpleHandler)))

	mh := skill.NewMuxHelper(mux, "")
	mh.F("/simple3", simpleFunc)
	mh.H("/simple4", new(simpleHandler))

	server := http.Server{
		Handler: mux,
	}

	server.ListenAndServe()
}

func simpleFunc(ctx *skill.Context) {
	ctx.WriteSimpleText("simple text")
}

type simpleHandler int

func (h simpleHandler) Handle(ctx *skill.Context) {
	ctx.WriteSimpleText("simple text")
}
$ go run example.go

Usage

Response Code
  • 200 OK
    • 아래 호출 시
      • Context.WriteSimpleText
      • Context.WriteSimpleImage
      • Context.WriteResponse
  • 204 No Content
    • Context.Write~~~ 시리즈 함수가 호출되지 않고 핸들러가 종료되었을 때
  • 400 Bad Request
    • MethodPOST 가 아닐 때
  • 406 Not Acceptable
    • skill.AllowedRemoteAddr 가 설정되어 있고, 목록에 없는 아이피일 때
  • 500 Internal Error
    • payload 파싱에 실패했을 때. (panic)
카카오톡 스킬 서버 IP
  • skill.AllowedRemoteAddr 에서 접근을 허용할 IP 를 지정해줄 수 있습니다.
  • skill.AllowedRemoteAddr 를 비워주시면 모든 IP 대역에서의 접근이 허용됩니다.
  • 기본값으로 아래 IP 가 선언되어 있습니다.
    • 219.249.231.40
    • 219.249.231.41
    • 219.249.231.42
  • nginxproxy_pass 와 같은 서비스 사용시 아래와 같이 설정해주세요
    • skill.FP skill.HP 함수를 사용해주세요.

      • Request Header 에서 찾으면 해당 헤더의 값을, 없으면 Request.RemoteAddr 필드가 사용됩니다.
    • 예시

      • nginx.conf
      ...
      
      location ... {
          proxy_pass ...;
          proxy_set_header X-Real-IP $remote_addr;
      }
      
      ...
      
      • main.go
      // example.go
      package main
      
      import (
          "net/http"
      
          skill "github.com/RyuaNerin/go-kakaoskill/v2"
      )
      
      func main() {
          mux := http.NewServeMux()
          mux.HandleFunc("/simple1", skill.FP("X-Real-IP", simpleFunc))
          mux.Handle("/simple2", skill.HP("X-Real-IP", new(simpleHandler)))
      
          mh := skill.NewMuxHelper(mux, "X-Real-IP")
          mh.F("/simple3", simpleFunc)
          mh.H("/simple4", new(simpleHandler))
      
          server := http.Server{
              Handler: mux,
          }
      
          server.ListenAndServe()
      }
      
      func simpleFunc(ctx *skill.Context) {
          ctx.WriteSimpleText("simple text")
      }
      
      type simpleHandler int
      
      func (h simpleHandler) Handle(ctx *skill.Context) {
          ctx.WriteSimpleText("simple text")
      }
      

Documentation

Index

Constants

This section is empty.

Variables

View Source
var AllowedRemoteAddr = []string{
	"219.249.231.40",
	"219.249.231.41",
	"219.249.231.42",
}

카카오톡 스킬 서버의 IP 입니다. nil 로 설정하면 모든 IP 에서 접근을 허용합니다.

Functions

func F

skill.HandleFunc -> http.HandlerFunc

func FP

func FP(headerName string, fn HandleFunc) http.HandlerFunc

skill.HandleFunc -> http.HandlerFunc (with proxy_pass)

func H

skill.Handler -> http.HandlerFunc

func HP

func HP(headerName string, h Handler) http.HandlerFunc

skill.Handler -> http.HandlerFunc (with proxy_pass)

Types

type Action

type Action struct {
	Id           string                 `json:"id"`           // 스킬의 고유한 식별자입니다.
	Name         string                 `json:"name"`         // 설정된 스킬의 이름입니다.
	Params       map[string]interface{} `json:"params"`       // 사용자의 발화로부터 추출한 파라미터 정보입니다.
	DetailParams map[string]DetailParam `json:"detailParams"` // 사용자의 발화로부터 추출한 엔티티의 상세 정보입니다.
	ClientExtra  map[string]interface{} `json:"clientExtra"`  // 사용자의 발화의 추가적인 정보
}

type BasicCard

type BasicCard struct {
	Title       string     `json:"title,omitempty"`
	Description string     `json:"description,omitempty"`
	Thumbnail   *Thumbnail `json:"thumbnail,omitempty"`
	Buttons     []Button   `json:"buttons,omitempty"`
}

기본 카드형 출력 요소입니다. 기본 카드는 소셜, 썸네일, 프로필 등을 통해서 사진이나 글, 인물 정보 등을 공유할 수 있습니다. 기본 카드는 제목과 설명 외에 썸네일 그룹, 프로필, 버튼 그룹, 소셜 정보를 추가로 포함합니다.

type Block

type Block struct {
	Id   string `json:"id"`   // 블록 ID
	Name string `json:"name"` // 블록 이름
}

type Bot

type Bot struct {
	Id   string `json:"id"`   // 봇의 고유한 식별자입니다.
	Name string `json:"name"` // 설정된 봇의 이름입니다.
}

type Button

type Button struct {
	Label      string `json:"label"`                // 버튼에 적히는 문구입니다 (최대 8자)
	Action     string `json:"action"`               // 버튼 클릭시 수행될 작업입니다
	WebLinkUrl string `json:"webLinkUrl,omitempty"` // 웹 브라우저를 열고 webLinkUrl 의 주소로 이동합니다 (Action: webLink)
	OsLink     *Link  `json:"osLink,omitempty"`     // osLink 값에 따라서 웹의 주소로 이동하거나 앱을 실행합니다 (Action: osLink)
	// Action: "message" / "block"
	// message => 사용자의 발화로 messageText를 내보냅니다. (바로가기 응답의 메세지 연결 기능과 동일)
	// block => 블록 연결시 사용자의 발화로 노출됩니다.
	MessageText string                 `json:"messageText,omitempty"`
	PhoneNumber string                 `json:"phoneNumber,omitempty"` // phoneNumber에 있는 번호로 전화를 겁니다 (전화번호)
	BlockId     string                 `json:"blockId,omitempty"`     // blockId를 갖는 블록을 호출합니다 (바로가기 응답의 블록 연결 기능과 동일)
	Extra       map[string]interface{} `json:"extra,omitempty"`       // block이나 message action으로 블록 호출시, 스킬 서버에 추가적으로 제공하는 정보
}

action 종류 webLink : 웹 브라우저를 열고 webLinkUrl 의 주소로 이동합니다. osLink : osLink 값에 따라서 웹의 주소로 이동하거나 앱을 실행합니다. message : 사용자의 발화로 messageText를 실행합니다. (바로가기 응답의 메세지 연결 기능과 동일) phone : phoneNumber에 있는 번호로 전화를 겁니다. block : blockId를 갖는 블록을 호출합니다. (바로가기 응답의 블록 연결 기능과 동일)

messageText가 있다면, 해당 messageText가 사용자의 발화로 나가게 됩니다.
messageText가 없다면, button의 label이 사용자의 발화로 나가게 됩니다.

share : 말풍선을 다른 유저에게 공유합니다. share action은 특히 케로셀을 공유해야 하는 경우 유용합니다. operator : 상담원 연결 기능을 제공합니다. (베타)

type CarouselHeader

type CarouselHeader struct {
	Title       string     `json:"title"`                 // 케로셀 헤드 제목 (최대 2줄, 한 줄에 들어갈 수 있는 글자 수는 기기에 따라 달라집니다.)
	Description string     `json:"description,omitempty"` // 케로셀 헤드 설명 (최대 3줄, 한 줄에 들어갈 수 있는 글자 수는 기기에 따라 달라집니다.)
	Thumbnail   *Thumbnail `json:"thumbnail,omitempty"`   // 케로셀 헤드 배경 이미지 (현재 imageUrl 값만 지원합니다.)
}

type CommerceCard

type CommerceCard struct {
	Type   string         `json:"type"`             // 케로셀의 타입입니다.	("basicCard" 혹은 "commerceCard")
	Items  []interface{}  `json:"items"`            // 케로셀 아이템입니다 (BasicCard or CommerceCard, 최대 10개)
	Header CarouselHeader `json:"header,omitempty"` // 케로셀의 커버를 제공합니다 (CommerceCard 만 지원하고 있습니다. 추후 BasicCard 도 지원할 예정입니다.)
}

케로셀은 여러 장의 카드를 하나의 메세지에 일렬로 포함하는 타입입니다.

type Component

type Component struct {
	SimpleText   *SimpleText   `json:"simpleText,omitempty"`   // 간단 텍스트
	SimpleImage  *SimpleImage  `json:"simpleImage,omitempty"`  // 간단 이미지
	BasicCard    *BasicCard    `json:"basicCard,omitempty"`    // 기본 카드 (캐로샐 가능)
	CommerceCard *CommerceCard `json:"commerceCard,omitempty"` // 커머스 카드 (캐로샐 가능)
	ListCard     *ListCard     `json:"listCard,omitempty"`     // 리스트 카드
}

type Context

type Context struct {
	ResponseWriter http.ResponseWriter
	Reqeust        *http.Request
	Payload        *SkillPayload
	// contains filtered or unexported fields
}

func (*Context) WriteResponse

func (ctx *Context) WriteResponse(res *SkillResponse)

func (*Context) WriteSimpleImage

func (ctx *Context) WriteSimpleImage(imageUrl string, altText string)

func (*Context) WriteSimpleText

func (ctx *Context) WriteSimpleText(str string)

type ContextControl

type ContextControl struct {
	Values []ContextValue `json:"values"`
}

context control 필드는 블록에서 생성한 outputContext의 lifeSpan, params 등을 제어할 수 있습니다.

type ContextValue

type ContextValue struct {
	Name     string            `json:"name"`             // 수정하려는 output 컨텍스트의 이름
	LifeSpan string            `json:"lifeSpan"`         // 수정하려는 ouptut 컨텍스트의 lifeSpan
	Params   map[string]string `json:"params,omitempty"` // output 컨텍스트에 저장하는 추가 데이터
}

type DetailParam

type DetailParam struct {
	Origin    interface{} `json:"origin"`
	Value     interface{} `json:"value"`
	GroupName string      `json:"groupName"`
}

type HandleFunc

type HandleFunc func(ctx *Context)

func (HandleFunc) Handle

func (hf HandleFunc) Handle(ctx *Context)

type Handler

type Handler interface {
	Handle(ctx *Context)
}
type Link struct {
	Mobile  string `json:"mobile,omitempty"`  // ios와 android를 아우르는 mobile link입니다.
	Ios     string `json:"ios,omitempty"`     // ios의 웹이나 앱을 실행하는 link입니다.
	Android string `json:"android,omitempty"` // android의 웹이나 앱을 실행하는 link입니다.
	Pc      string `json:"pc,omitempty"`      // mac과 window를 아우르는 pc link입니다.
	Mac     string `json:"mac,omitempty"`     // mac의 웹이나 앱을 실행하는 link입니다.
	Win     string `json:"win,omitempty"`     // window의 웹이나 앱을 실행하는 link입니다.
	Web     string `json:"web,omitempty"`     // 모든 기기를 아우르는 link입니다.
}

링크는 다음과 같은 우선순위를 갖습니다. 모바일: web < mobile < ios or android (os에 따라 적용) pc: web < pc < mac or win (os에 따라 적용))

type ListCard

type ListCard struct {
	Header  ListItemHeader  `json:"header"`            // 카드의 상단 항목
	Items   []ListItemItems `json:"items"`             // 카드의 각각 아이템 (최대 5개)
	Buttons []Button        `json:"buttons,omitempty"` // 최대 2개
}

리스트 카드형 출력 요소입니다. 리스트 카드는 표현하고자 하는 대상이 다수일 때, 이를 효과적으로 전달할 수 있습니다. 헤더와 아이템을 포함하며, 헤더는 리스트 카드의 상단에 위치합니다. 리스트 상의 아이템은 각각의 구체적인 형태를 보여주며, 제목과 썸네일, 상세 설명을 포함합니다.

type ListItemHeader

type ListItemHeader struct {
	Title    string `json:"title"`    // listCard의 제목
	ImageUrl string `json:"imageUrl"` // listCard 제목의 배경
	Link     Link   `json:"link"`     // 클릭시 작동하는 링크입니다.
}

type ListItemItems

type ListItemItems struct {
	Title       string `json:"title"`                 // 제목
	Description string `json:"description,omitempty"` // 설명
	ImageUrl    string `json:"imageUrl"`              // 우측 안내 사진
	Link        Link   `json:"link"`                  // 클릭시 작동하는 링크입니다.
}

type MuxHelper added in v2.0.1

type MuxHelper struct {
	// contains filtered or unexported fields
}

ServeMux 핸들러 처리를 편하게 해주는 유틸리티

func NewMuxHelper added in v2.0.1

func NewMuxHelper(mux *http.ServeMux, remoteAddrHeaderName string) *MuxHelper

mux : nil 이면 http.DefaultServeMux 를 사용합니다.

func (*MuxHelper) F added in v2.0.1

func (m *MuxHelper) F(pattern string, fn HandleFunc)

func (*MuxHelper) H added in v2.0.1

func (m *MuxHelper) H(pattern string, h Handler)

type Profile

type Profile struct {
	Nickname string `json:"nickname"` // 프로필 이름
	ImageUrl string `json:"imageUrl"` // 프로필 이미지
}

type QuickReply

type QuickReply struct {
	Label       string      `json:"label"`       // 사용자에게 노출될 바로가기 응답의 표시
	Action      string      `json:"action"`      // 바로가기 응답의 기능 (message or block)
	MessageText string      `json:"messageText"` // 사용자 측으로 노출될 발화
	BlockId     string      `json:"blockId"`     // 바로가기 응답이 'block' 일 때 연결될 블록의 id
	Extra       interface{} `json:"extra"`       // 블록을 호출 시 추가적으로 제공하는 정보
}

바로가기 응답은 발화와 동일합니다. 대신, 사용자가 직접 발화를 입력하지 않아도 선택을 통해서 발화를 전달하거나 다른 블록을 호출할 수 있습니다.

type SimpleImage

type SimpleImage struct {
	ImageUrl string `json:"imageUrl"` // 전달하고자 하는 이미지의 url입니다 (URL 형식)
	AltText  string `json:"altText"`  // url이 유효하지 않은 경우, 전달되는 텍스트입니다 (1000자 이내)
}

간단한 이미지형 출력 요소입니다. 이미지 링크 주소를 포함하면 이를 스크랩하여 사용자에게 전달합니다. 이미지 링크 주소가 유효하지 않을 수 있기 때문에, 대체 텍스트를 꼭 포함해야 합니다.

type SimpleText

type SimpleText struct {
	Text string `json:"text"` // 전달하고자 하는 텍스트입니다 (1000자 이내)
}

간단한 텍스트형 출력 요소입니다.

type SkillPayload

type SkillPayload struct {
	UserRequest UserRequest `json:"userRequest"`
	Bot         Bot         `json:"bot"`
	Action      Action      `json:"action"`
}

type SkillResponse

type SkillResponse struct {
	Version  string                 `json:"version"`           // must "2.0"
	Template SkillTemplate          `json:"template"`          // 스킬 응답의 출력 모양을 담고 있는 항목입니다. 출력으로 사용할 요소 그룹, 바로가기 응답 그룹 등을 포함합니다.
	Context  *ContextControl        `json:"context,omitempty"` // 블록의 context 설정을 제어할 수 있습니다.
	Data     map[string]interface{} `json:"data,omitempty"`    //필요에 따라 커스텀한 데이터를 넣을 수 있는 항목입니다.
}

type SkillTemplate

type SkillTemplate struct {
	Outputs      []Component  `json:"outputs"`                // 출력 그룹(outputs)은 여러 종류의 출력 요소(component)를 포함합니다 (1개 이상 3개 이하)
	QuickReplies []QuickReply `json:"quickReplies,omitempty"` // 바로가기 그룹(quickReplies)은 여러 개의 바로가기 요소(quickReply)를 포함합니다 (10개 이하)
}

type Thumbnail

type Thumbnail struct {
	ImageUrl string `json:"imageUrl"`       //이미지의 url입니다.
	Link     *Link  `json:"link,omitempty"` // 이미지 클릭시 작동하는 link입니다.
	// true: 이미지 영역을 1:1 비율로 두고 이미지의 원본 비율을 유지합니다. 이미지가 없는 영역은 흰색으로 노출합니다.
	// false: 이미지 영역을 2:1 비율로 두고 이미지의 가운데를 크롭하여 노출합니다.
	FixedRatio bool `json:"fixedRatio"`
	Width      int  `json:"width"`  // fixedRatio를 true로 설정할 경우 필요한 값입니다. 실제 이미지 사이즈와 다른 값일 경우 원본이미지와 다르게 표현될 수 있습니다.
	Height     int  `json:"height"` // fixedRatio를 true로 설정할 경우 필요한 값입니다. 실제 이미지 사이즈와 다른 값일 경우 원본이미지와 다르게 표현될 수 있습니다.
}

type User

type User struct {
	Id         string       `json:"id"`         // 사용자를 식별할 수 있는 key로 최대 70자의 값을 가지고 있습니다.
	Type       string       `json:"type"`       // 현재는 botUserKey만 제공합니다.
	Properties UserProperty `json:"properties"` // 추가적으로 제공하는 사용자의 속성 정보입니다.
}

type UserProperty

type UserProperty struct {
	PlusFriendUserKey string `json:"plusfriendUserKey"` // 카카오톡 채널에서 제공하는 사용자 식별키 입니다.
	AppUserId         string `json:"appUserId"`         // 봇 설정에서 앱키를 설정한 경우에만 제공되는 사용자 정보입니다.
}

type UserRequest

type UserRequest struct {
	Timezone  string `json:"timezone"`  // 사용자의 시간대를 반환합니다.
	Block     Block  `json:"block"`     // 사용자의 발화에 반응한 블록의 정보입니다.
	Utterance string `json:"utterance"` // 봇 시스템에 전달된 사용자의 발화입니다.
	Lang      string `json:"lang"`      // 사용자의 언어를 반환합니다.
	User      User   `json:"user"`      // 사용자의 정보입니다.
}

Directories

Path Synopsis
example.go
example.go

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL