SharePointの画面にチャットボットを組み込みたいという話があったので、前に作ったチャットボットを流用して実現してみました。
その手順や気づいたことを書き留めようと思います。
はじめに
SharePointに自分で機能を追加するのにSharePoint Frameworkが用意されてました。
SharePoint Frameworkでは、以下の種類のコンポーネントを開発できるそうです。
- Webパーツ
- ページ内に表示される部品。
- 拡張機能
- アプリケーション・カスタマイザ
- スクロールしても表示が残るヘッダやフッタなど。
- フィールド・カスタマイザ
- リストの列の見た目を変える。
- ListViewコマンド・セット
- リストにボタンを追加して、処理を実行できるようにする。
- アプリケーション・カスタマイザ
- ライブラリ
- 他のコンポーネントから利用できる部品。
今回はアプリケーション・カスタマイザで開発するのが良いと判断しました。
この記事ではSharePoint Frameworkのバージョン1.12.1を使用しています。
開発環境のセットアップ
この手順に従ってGulp, Yeoman, YeomanのSharePointジェネレーターをインストール。
Node.jsはサポートされているバージョンがインストール済みだったので割愛。
$ npm install gulp yo @microsoft/generator-sharepoint --global
プロジェクトの作成
この手順で、まずプロジェクト用のchatbotディレクトリを作成し、そのディレクトリ配下で以下のコマンドを実行。
$ yo @microsoft/sharepoint
_-----_
| | .--------------------------.
|--(o)--| | Welcome to the |
`---------´ | SharePoint Client-side |
( _´U`_ ) | Solution |
/___A___\ | Generator@1.12.1 |
| ~ | '--------------------------'
__'.___.'__
´ ` |° ´ Y `
Let's create a new SharePoint solution.
? What is your solution name? chatbot
? Which baseline packages do you want to target for your component(s)? SharePoint Online only (latest)
? Where do you want to place the files? Use the current folder
Found npm version 6.14.11
? Do you want to allow the tenant admin the choice of being able to deploy the solution to all sites immediately without running any feature deployment or adding apps in sites? No
? Will the components in the solution require permissions to access web APIs that are unique and not shared with other components in the tenant? No
? Which type of client-side component to create? Extension
? Which type of client-side extension to create? Application Customizer
Add new Application Customizer to solution chatbot.
? What is your Application Customizer name? Chatbot
? What is your Application Customizer description? User assistant.
- 拡張機能の手順に、Do you want to allow the tenant admin〜とWill the components in the solution require permissions〜は載ってませんでしたが、Webパーツの方にあったので、それに従ってデフォルトのNにしました。
なお、最初にプロジェクトを作成した時だけ、以下のコマンドで開発者用自己署名証明書の信頼を行います。
gulp trust-dev-cert
フッタの実装
プレースホルダーのサンプルを参考に、まずは中身のないフッタだけを作成します。
.app {
position: relative;
height: 1px;
display: flex;
}
import { override } from '@microsoft/decorators';
import {
BaseApplicationCustomizer, PlaceholderContent, PlaceholderName
} from '@microsoft/sp-application-base';
import styles from './ChatbotCustomizer.module.scss';
/**
* If your command set uses the ClientSideComponentProperties JSON input,
* it will be deserialized into the BaseExtension.properties object.
* You can define an interface to describe it.
*/
export interface IChatbotApplicationCustomizerProperties {
}
/** A Custom Action which can be run during execution of a Client Side Application */
export default class ChatbotApplicationCustomizer
extends BaseApplicationCustomizer<IChatbotApplicationCustomizerProperties> {
private _bottomPlaceholder: PlaceholderContent | undefined;
@override
public onInit(): Promise<void> {
this.context.placeholderProvider.changedEvent.add(this, this._renderPlaceHolders);
return Promise.resolve();
}
private _renderPlaceHolders(): void {
if (!this._bottomPlaceholder) {
this._bottomPlaceholder = this.context.placeholderProvider.tryCreateContent(PlaceholderName.Bottom);
if (this._bottomPlaceholder.domElement) {
this._bottomPlaceholder.domElement.innerHTML
= `<div class="${styles.app}"></div>`;
}
}
}
}
- VS Code上で編集していると、最初はscssファイルをインポートする部分でエラーが発生しますが、以降の手順でビルドが行われると、解消されます。
テスト
serve.jsonのpageUrlを拡張機能を組み込む予定のSharePointのURLに変更し、プロパティは使わないので削除します。
{
"$schema": "https://developer.microsoft.com/json-schemas/core-build/serve.schema.json",
"port": 4321,
"https": true,
"serveConfigurations": {
"default": {
"pageUrl": "https://hogehoge.sharepoint.com/sites/portal",
"customActions": {
"da62dff0-4c91-4aed-a978-0e4a95fa289b": {
"location": "ClientSideExtension.ApplicationCustomizer"
}
}
},
"chatbot": {
"pageUrl": "https://hogehoge.sharepoint.com/sites/portal",
"customActions": {
"da62dff0-4c91-4aed-a978-0e4a95fa289b": {
"location": "ClientSideExtension.ApplicationCustomizer"
}
}
}
}
}
- VS Codeで開くと、
Property serveConfigurations is not allowed.
って警告が表示されるけど、指定したURLとか正常に機能しているから、気にしないで良さそうです。
そしてgulp serve
を実行するとブラウザにページが表示されて、以下の確認画面が表示されるので、[デバッグ スクリプト を読み込む]をクリック。
- ビルドされたJavaScript等が、gulp serveによりポート4321で公開され、ここで読み込まれるという仕組みのようです。
すると画面上では何も見えませんが、DOMツリー上で高さ1pxのフッタが追加されていることが確認できます。
チャットボットを組み込む
今回のアプローチとしてチャットボットのコードをプロジェクトに移植するのではなく、こちらを参考に、Svelteで作ったチャットボットのjsファイルをそのまま組み込むことにしました。
実装は簡単で、jsファイルをプロジェクト内に配置し、カスタマイザのonInitメソッド内でrequireします。
@override
public onInit(): Promise<void> {
require('../../../assets/bundle.js');
this.context.placeholderProvider.changedEvent.add(this, this._renderPlaceHolders);
return Promise.resolve();
}
private _renderPlaceHolders(): void {
// 割愛
this._bottomPlaceholder.domElement.innerHTML = `
<div class="${styles.app}">
<chat-frame title="お問い合わせ" closeclass="${styles.close}"></chat-frame>
</div>`;
あとはチャットボットのスタイルをChatbotCustomizer.module.scssに指定します。
- CSSのクラス名はカプセル化(例:app→app_22ddff86)されるので、クラス名を直に指定するのではなく、${styles.app}のように変数で指定する。
リリース版のビルドをする
まず、手順と同様に、サイトレベルに拡張機能をリリースすることにして、/config/package-solution.jsonからClientSideInstance.xmlへの指定を削除します。
そして、以下を実行してリリース版のビルドを行います。
gulp bundle --ship
gulp package-solution --ship
アプリカタログにリリースする
ビルドでできあがった/sharepoint/solution/chatbot.sppkgをアプリカタログにリリースします。
-
まだアプリカタログがない場合は、ここを参照。
- ただ、[Web サイトのアドレス サフィックス]を例のまま「アプリ」にしたら、うまくリリースできない現象に遭遇しました。URLに使われるので英語が無難なようです。
-
手順では分かりづらいですが、アプリカタログのサイトで[SharePoint用アプリ]をクリックして、sppkgファイルをドラッグ&ドロップします。
サイトにインストールする
アプリをインストールするサイトの[サイトコンテンツ]ページを開き、[新規]から[アプリ]をクリックします。
表示されたページからアプリをクリックすると、インストールが行われます。
気づいたこと
- スタイルにopacityを使うと、ビルド後は指定した値が無視されて1%(透明になって見えなくなる)になります。
- アプリを削除したい場合、サイトコンテンツをクラシック表示する必要があります。
- アプリをバージョンアップしたい場合、/config/package-solution.json内のversionを更新して、アプリカタログに再リリースします。