チームスピリットデベロッパーブログ

チームスピリット開発者のブログ

Salesforce World Tour Tokyo2016ミニハックの解答例を公開します

みなさんこんにちは。
株式会社チームスピリット エンジニアの山﨑(id:dackdive)です。

このたび、弊社の技術ブログをはてなブログに移行しました!
(以前は TeamSpirit 魂のブログ に投稿していました)

記念すべき初回の記事は昨日、一昨日に行われた Salesforce World Tour Tokyo の話をさせていただきます。

私も昨日は終日参加させていただきましたが、開発者向けゾーンも年々盛り上がりを見せている気がします。

f:id:dackdive:20161214110305j:plain

f:id:dackdive:20161214150236j:plain

ところで、こういった Salesforce の年次イベントでは恒例となっていますが
今回もミニハックという開発者向けクイズがありました。

https://developer.salesforce.com/ja/worldtour2016/minihacks

  • 今回は事前に内容を公開
  • 正解者には抽選で豪華景品が当たる!
  • 1問正解で抽選券1口なので、解けば解くほどお得

ということで、私も豪華景品をゲットすべく挑戦してみました。
せっかくですのでその内容を以下のリポジトリで公開しています。

すべて、Force.com Migration Tool を使ってデプロイ可能な状態にしております。

以下、各課題の簡単な解説です。


課題1 - 出張申請を楽にする

毎回登場する、いわゆるポイント&クリックツールだけを使用してアプリケーションを構築しよう、というお題です。
Salesforce プラットフォームへの幅広い知識が問われ、私が最も苦手とする分野でもあります。

  1. 予定額が700ドルを超える出張申請は、承認が必要となるため、申請者の上司に自動送信する必要があります。

をどう実現するかがポイントでしょうか。私はプロセスビルダーを使用しましたが、他にやり方あるのかな?


課題 2 - オールインワンシステム

「外部データベースシステム」から Salesforce Connect を連想できれば簡単ですね。
(Salesforce Connect については Trailhead のこのモジュール をやるとよさげ)

わからなかったこと

外部データソースを作成する際、「種別」で「Salesforce Connect: OData 4.0」を選ぶとうまく同期できなかったので、何も考えず「Salesforce Connect: OData 2.0」を選択してしまいましたが
判断する基準とかあるんでしょうか。


課題3 - Visualforceのデザインを変更する

参考ブログ の通りにやるだけ、かと思ったら
独自 namespace を追加した Lightning Design System を適用するためにコードを一部修正する必要があったり
そもそも元のコードの createAccount() に相当するロジック部分がまるっとなかったりで
意外とやることが多い課題だったように思います。

勘のいい方は参考ブログに貼られている Demo Page のコードをブラウザの開発者コンソールで開いて
createAccount() 部分をまるっとコピーして楽をしたのではないでしょうか。(私だけ?)

なお、今回 CRUD 処理は参考ブログと同じく Remote Objects を利用しています。
単純なオブジェクト操作を行うページであれば、Apex の実装不要で実現できるので便利ですね。

それから、これは参考ブログを読んで初めて知りましたが
Force.com サイト という機能を使うと Visualforce ページを一般公開できるんですね。
私も自分で作ったページを公開してみましたが、こんな感じです。
http://yama-swtt16minihacks-developer-edition.ap2.force.com/

公開する際は、静的リソースのキャッシュを「公開」に設定することに注意。

f:id:dackdive:20161215104558p:plain


課題4 - Lightningを使った取引先責任者検索

ベーシックな Lightning Component のお題。
いつぞやの Salesforce Lightning コンポーネントチュートリアル とほとんど同じ内容だったので、
取引先名で検索しないといけない ことさえ注意すればほとんどコピペでいけたはず。

私は、せっかく取り組むので Lightning 基本コンポーネントと Lightning Data Service を使って実現できないかなと思ったんですが
<lightning:input> タグが onChange イベント時に event.target.value で値を拾うことができなかったり
Lightning Data Service は複数レコードを扱うようなタグは今のところなかったようなので
結局どちらも断念。オーソドックスな作りとなりました。
(課題1 で作った Lightning Design System の静的リソースを利用して見た目だけはそれっぽくしましたが…)

f:id:dackdive:20161215105355p:plain


課題5 - Herokuアプリケーションを使ってみる

サンプルコードが Python というだけで諦めた 方も多かったのではないでしょうか。
Python は良い言語です。大丈夫、怖くない。

ただ、参考ブログ のセットアップ周りの内容が Python 未経験者には敷居が高いんじゃないかなーという印象です。
実際ローカルで動くようにしなくてもクリアできますしね。

本番環境の DATABASE_URL をコピーしてローカル開発でも本番環境の DB を使う、というのは知らなかったなあ。


課題6 - APIを使いこなす

  1. RESTリソースを更新して、取引先責任者の説明の項目を「アクティブでない取引先責任者」に更新できるようにしてください。

の自由度が高く、皆さんどういう実装をしたのか気になります。
私は Id を PUT で送ると説明欄だけ更新するようなメソッドを作りました。

@HttpPut
global static void deactivate(Id contactId) {
    RestRequest req = RestContext.request;
    RestResponse res = RestContext.response;
                                                          
    Contact contact = new Contact(Id = contactId);
    contact.Description = 'アクティブでない取引先責任者';
    update contact;
}
わからなかったこと
  1. サンプルコードと同様に、認証には、ユーザー名とパスワードの代わりにセッションIDを使用して、組織のREST APIを呼び出し、ソリューションをデモできます。

と記載がありながら、私はセッションIDの取得部分は Force.com REST API 開発者ガイド

curl https://login.salesforce.com/services/oauth2/token -d "grant_type=password" -d "client_id=myclientid" -d "client_secret=myclientsecret" 
    -d "username=mylogin@salesforce.com" -d "password=mypassword123456"

と同じように、ユーザー名とパスワードを使ってしまいました。
少なくともターミナルなどの環境から実行する場合、セッションIDを取得する処理については仕方ないのかな…?


課題7 - LINE株式会社からの課題 - LINE Messaging APIを使ったLINE Botの構築

流行りの Bot です。

サンプルコードを Heroku にデプロイした後、/salesforce にアクセスするところまではたどり着いたものの
以下の認証コードをどこで送信すればいいかわからなくてつまづいた方も多そう。

f:id:dackdive:20161215133716p:plain:w320

Bot との 1 on 1 トークは制限されるようなので、普通にグループに Bot を招待してあげて送信すればよかったんですね。
またその際、Bot のグループトーク参加を許可しておくことも忘れずに。
私はこれでしばらくハマりました。

f:id:dackdive:20161215134400p:plain


おわりに

というわけで、ミニハックの内容を一通り紹介しました。
気になる課題についてはぜひリポジトリのコードを読んでみたり、実際にデプロイして動かしてみたりしていただければ。

f:id:dackdive:20161214190045j:plain

帰り際、最後にぽつんと残された巨大アストロ君。
心なしか 全問正解なのに抽選会で見事に1つも当たらなかった 時の私と同じ目をしています。