ドキュメント

コンテンツプレビュー機能に対応したWebサーバを実装する

本チュートリアルでは、コンテンツプレビュー機能に対応したWebサーバを実装する方法の一例を解説します。サンプルコードはJavaScript (Node.js)で書かれていますが、他のプログラミング言語でも同様に実装できるように説明しています。

コンテンツプレビュー機能自体についての説明はこちらのリンク先をご確認ください。

コンテンツプレビュー機能に対応するには

コンテンツプレビュー機能に対応するためには、API設定の「コンテンツプレビュー」画面で「遷移先URL」に指定した形式のURLへのリクエストに対して、URLで指定されたコンテンツのプレビューページを返すようにする必要があります。すなわち、以下のような処理を行えるWebサーバが必要です。

  1. 遷移先URLに指定した形式のURLへのHTTP(S) GETリクエストを受け付け、
  2. リクエストURLからコンテンツIDとDraft-Tokenを抽出し、
  3. hacoCMSのAPIでコンテンツIDとDraft-Tokenを使って下書き状態のコンテンツを取得し、
  4. そのコンテンツのプレビューページを生成し、
  5. そのHTMLをレスポンスする。

本チュートリアルでは、/{CONTENT_ID}?draft={DRAFT_TOKEN}の形式のパスとクエリ文字列でコンテンツプレビューのリクエストを受け付けるWebサーバを実装します。サンプルコードはJavaScript (Node.js)ですが、他のプログラミング言語でも応用できるように説明します。

実装手順

Step 0. hacoCMSのAPIスキーマ設定

※サンプルコードに合わせたAPIを作成します。既にAPIがある場合はそちらを利用しても構いませんが、そのAPIスキーマに合わせて実装する必要があります。

お持ちのhacoCMSアカウントの適当なプロジェクト(無ければ作成してください)に、記事APIを以下の設定で作成してください。

  • API名:記事(任意)
  • エンドポイント:entries
  • 説明文:(任意)
  • APIの型:リスト形式
  • APIスキーマ:下記の表と画像を参照
# フィールドタイプ フィールド名(任意) フィールド ID
1 テキストフィールド タイトル title
2 テキストフィールド 概要 description
3 リッチテキスト 本文 body

APIスキーマの設定画面は以下のようになります。

記事APIを作成できたら、後ほど動作確認に使用する記事を作成し、下書き保存しておきましょう。

Step 1. リクエストを受け付けるWebサーバを作成

Node.jsに標準で用意されているhttpモジュールを使って、3000番ポートでHTTPリクエストを受け付けるWebサーバを用意します。他のプログラミング言語でも同様のモジュール等を利用して実装出来ると思います。

次のようなコードを書いて、index.jsというファイル名で保存してください。

import { createServer } from 'http'

const server = createServer((request, response) => {
  const body = '<h1>Hello, world</h1>\n'

  response.writeHead(200, {
    'Content-Type': 'text/html',
  })
  response.end(body)
})

const port = 3000
server.listen(port)

node index.jsコマンドを実行し、ブラウザでhttp://localhost:3000/を開いてください。「Hello, world」と表示されることを確認してください。

Step 2. リクエストURLのコンテンツIDとDraft-Tokenをパース

リクエストURLに含まれるコンテンツIDとDraft-Tokenをパースする必要があります。ここではNode.jsに標準で用意されているURLクラスを使って、リクエストURLからコンテンツIDとDraft-Tokenをパースします。

index.jsに、URLクラスのオブジェクトからCONTENT_IDDRAFT_TOKENを抽出する、次のような関数をcreateServerの前に追加してください。

const parseParams = (url) => ({
  CONTENT_ID: url.pathname.slice(1),
  DRAFT_TOKEN: url.searchParams.get('draft'),
})

リクエストハンドラ(createServerの引数)からこの関数を呼び出し、レスポンスで確認できるように以下のように変更してください。

const server = createServer((request, response) => {
  const url = new URL(request.url, `http://${request.headers.host}`)

  // リクエスト URL の CONTENT_ID と DRAFT_TOKEN をパース
  const { CONTENT_ID, DRAFT_TOKEN } = parseParams(url)

  const body = `CONTENT_ID: ${CONTENT_ID}\nDRAFT_TOKEN: ${DRAFT_TOKEN}\n`

  response.writeHead(200, {
    'Content-Type': 'text/html',
  })
  response.end(body)
})

node index.jsを再実行して、Step 0で作成したAPIの下書きコンテンツのコンテンツIDとDraft-Tokenを使って、http://localhost:3000/〈コンテンツID〉?draft=〈Draft-Token〉にブラウザでアクセスし、指定したコンテンツIDとDraft-Tokenが表示されることを確認してください。

Step 3. hacoCMS APIで下書き状態のコンテンツを取得

Step 2で得られたコンテンツIDとDraft-Tokenを使って、hacoCMSのAPIで下書き状態のコンテンツを取得します。JavaScriptまたはTypeScriptの場合はSDK(hacocms-js-sdk)を使って簡単に実装することができます。この他、執筆時点ではPHP, Java/Kotlin, SwiftでもSDKが利用できます。

SDKをインストール

下記のコマンドを実行してhacocms-js-sdkをインストールしてください。

npm init  # 質問される項目には任意に回答してください
npm install hacocms-js-sdk

また、.envファイルから環境変数をprocess.envに読み込めるようにするために、別途下記のコマンドでdotenvをインストールしてください。.envファイルを使わずに環境変数を設定する場合は不要です。

npm install dotenv

次のように環境変数を設定(.envファイルを作成)してください。

HACOCMS_PROJECT_SUBDOMAIN=〈プロジェクトのサブドメイン〉
HACOCMS_PROJECT_ACCESS_TOKEN=〈プロジェクトのAccess-Token〉

下書きコンテンツを取得

3箇所コードを追加・変更します。

まず、index.jsの最初に以下を追加してください。

import * as dotenv from 'dotenv'
import { ApiContent, HacoCmsClient } from 'hacocms-js-sdk'

次に、dotenvで.envファイルを読み込み、Step 0で作成したAPIスキーマに対応するクラスとAPIクライアントを生成するための、以下のコードをcreateServerより前に追加してください。

dotenv.config()  // dotenvをインストールしなかった場合は、この行は不要です

/** API のコンテンツに対応するクラス */
class ExampleContent extends ApiContent {
  constructor(json) {
    super(json)

    this.title = json.title
    this.description = json.description
    this.body = json.body
  }
}

const client = new HacoCmsClient(
  `https://${process.env.HACOCMS_PROJECT_SUBDOMAIN}.hacocms.com`,
  process.env.HACOCMS_PROJECT_ACCESS_TOKEN
)

そして、リクエストハンドラ(createServerの引数)のparseParamsの後に次のコードを追加してください。

  // SDK で API から下書き状態のコンテンツを取得
  const draft = await client.getContent(ExampleContent, '/entries', CONTENT_ID, DRAFT_TOKEN)

また、リクエストハンドラ(createServerの引数)のアロー関数をasyncにしてください。

ここまでできたらnode index.jsを再実行して、ブラウザをリロード(または同じURLに再度アクセス)して正常にレスポンスが返ってくる(Step 2と同じものが表示される)ことを確認してください。

Step 4. 取得したコンテンツをもとにプレビューを生成

Step 3で取得した下書きコンテンツのJSONからコンテンツのプレビューとなるHTMLを生成します。ここでは、JavaScriptのテンプレート文字列でコンテンツのタイトル等を埋め込む簡便な方法で実装します。

まず、記事コンテンツのJSONオブジェクトからHTMLの文字列を生成する関数を以下のように定義します。なお、説明のために一部のタグを省略しています。

/** API コンテンツから HTML を生成する関数 */
const generateHtml = (entry) => `
<h1>${entry.title}</h1>
<p>${entry.description}</p>
${entry.body}
`

次に、この関数で下書きコンテンツのJSONオブジェクトからHTML文字列を生成し、body変数に代入するように書き換えます。

  // コンテンツからレスポンス HTML を生成
  const body = generateHtml(draft)

これで、node index.jsを再実行してブラウザをリロードすれば、下書きコンテンツのプレビューが表示されるようになります。

実際に遷移先URLに設定できるようにするには

以上で、hacoCMSのコンテンツプレビュー機能に対応した簡易Webサーバが完成しました。これをインターネットからアクセスできるようにすることで、http://〈ドメイン〉/{CONTENT_ID}?draft={DRAFT_TOKEN}を(〈ドメイン〉をWebサーバのドメインに置き換えて)コンテンツプレビューの遷移先URLとして設定できるようになります。なお、HTTPSでの接続にはSSL/TLS証明書の準備など追加の手順が必要になります。

ただし、本チュートリアルで説明したサンプルコードではエラー処理等を省略しているため、実用するにはそれらの処理を追加する必要があります。

また、本チュートリアルのサンプルコードはWebフレームワークを使わない実装になっています。Webフレームワークを利用する場合、既存のWebサーバでコンテンツプレビュー機能に対応する場合や、サーバレスアーキテクチャの環境に実装する場合などは、それぞれの環境に合わせて実装する必要があります。