2
4

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.

[Python] Zendesk APIで HelpCenterの記事を検索するサンプル

Posted at

はじめに

Zendesk APIを使って、HelpCenterの記事を検索して取得するサンプルです。今回は認証にはAPI Tokenを使います。
あまりWebに情報が無いので、参考になればと思い書き残しておきます。
API利用開始までの手順は、本当はもっとあるのかもしれないですが、私の把握している範囲で書いています。

サンプルの環境

  • Python >= 3.6
  • requests

周辺知識

  • Zendesk APIは、一般的なREST & JSON というAPI。
  • 認証には 「メールアドレス」「API Token」が必要です。他にも「パスワード」「OAuth」による認証方式があります。
  • 「subdomain」を把握しておく必要があります。
    • 独自ドメインの場合、パット見のURLのHostとは違うので注意しましょう(私はこれが間違っててずっと 404エラーが出ていた...)。
  • APIは support API と help center API で何か違うらしい(検索される対象が違うようだ)
    • 認証方法などは共通のようだ

参考URL

準備

API Tokenを使うために、APIの利用開始とAPI Tokenの発行 を行います(参考URL参照)。

準備はこれくらいです。

コード

こんな感じで使えました。

from typing import List
import base64
from dataclasses import dataclass, field, fields

import requests


class ZendeskAPI:
    def __init__(self, sub_domain, email, password=None, api_token=None):
        assert password is not None or api_token is not None, 'please specify password or api_token'
        self.sub_domain = sub_domain
        self.email = email
        self.password = password
        self.api_token = api_token

    @property
    def api_host(self):
        return f'{self.sub_domain}.zendesk.com'

    @property
    def authorization_header_value(self):
        if self.password:
            content = f'{self.email}:{self.password}'
        else:
            content = f'{self.email}/token:{self.api_token}'
        return base64.b64encode(content.encode()).decode()

    def request(self, path, method="GET", params=None, data=None, json=None, retry=3):
        url = f'https://{self.api_host}{path}'
        headers = {
            'Authorization': f'Basic {self.authorization_header_value}',
        }

        response = None
        for _ in range(retry):
            response = requests.request(method, url, params=params, data=data, json=json, headers=headers)
            if response.status_code == 200:
                return response
            elif response.status_code < 500:
                break
        if response is not None:
            response.raise_for_status()

    def search_help_articles(self, keywords: List[str]):
        path = '/api/v2/help_center/articles/search.json'
        params = {'query': ",".join(keywords)}
        response = self.request(path, params=params).json()
        article_list = []
        for result in response.get('results') or []:
            article_list.append(populate(ZendeskArticle, result))
        return article_list


def populate(cls: dataclass, data, **kw):
    kwargs = {}
    dd = {}
    dd.update(data)
    dd.update(kw)
    for k in fields(cls):
        key = k.name
        kwargs[key] = dd.get(key)
    return cls(**kwargs)


@dataclass
class ZendeskArticle:
    id: str
    name: str
    title: str
    body: str = field(repr=False)
    label_names: List[str]
    url: str
    html_url: str
    author_id: str
    vote_sum: int = 0


api = ZendeskAPI(ZENDESK_SUB_DOMAIN, ZENDESK_EMAIL, api_token=ZENDESK_API_TOKEN)
articles = api.search_help_articles(['事例'])

for a in articles:
    print(a)

ZendeskArticle(id=8888888, name='提案時のアイデア集', title='提案時のアイデア集', label_names=['事例', 'アイデア', '提案'], url='https://...json', html_url='https://...%E9%9B%86', author_id=99999999, vote_sum=1)
ZendeskArticle(id=888888, ...)
...

あとは煮るなり焼くなり、、、ですね。

さいごに

小ネタでした。

2
4
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
2
4

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?