例: Salesforce オポチュニティー管理用のカスタム Process App の作成
プロセスアプリとは?
プロセスアプリは、特定のユースケースの分析を成功させるための一連の機能である。 例えば、プロセスアプリは、特定のプロセスマイニングシナリオのデータの抽出、変換、ロード(ETL)を自動化することができる。
詳細はプロセスアプリを参照。
カスタムプロセスアプリとは?
カスタムプロセス・アプリは、あなた自身で作成し、あなたの特定のユースケースに合わせて調整することができるアプリです。 カスタムプロセスアプリは、特定のケースを分析したいビジネスアナリストが使用できる。 プロセス・アプリ・ビルダー機能には、ビジネス・アナリストが特定のユースケースに関する洞察を得るために必要な要素を網羅した、事前定義された分析ダッシュボードのセットが付属している。
カスタム・プロセス・アプリを構築するには、ユースケース、分析したいプロセス、強調したいビジネス・インサイトを十分に理解する必要がある。 ETLプロセス(データ抽出、変換、ロード)は、 Python ロジックファイルで提供されなければならないため、カスタムプロセスアプリの構築にはコーディングスキルも必要となる。
詳細は、 カスタムプロセスアプリを参照。
Salesforce 機会管理のためのカスタムプロセスアプリの作成
オポチュニティー管理プロセスの最初のステップは、 Salesforceでオポチュニティーを作成することです。その後、一連のプロセスまたはプロセス・バリアントが続きます。 クローズされたオポチュニティーのデータが保管され、将来のアクションまたは参照のために分析されます。
Salesforce Salesforce 機会管理プロセスからデータを抽出、変換、およびロードするために使用します。 Salesforce Opportunities Process App 用の Python スクリプトは、 OpportunityCreation プロセスおよび OpportunityChange プロセス内のイベントのデータを抽出する必要があります。 さらに、データには以下のイベント属性が必要です。
opportunityIdactivitystartTimeresourceopportunityAmountopportunityStage
開始前に
カスタム・プロセス・アプリの作成を開始する前に、以下の必須設定を完了しておく必要があります:
IDPフォーマットのマッピングデータについては、 IBM Process Mining のプロセスのバックアップファイルをダウンロードしてください。組織の Salesforce インスタンスにアカウントを作成します。 ユーザー名とパスワードは、今後プロセスアプリで使用するために覚えておいてください。
あなたの IBM Process MiningSalesforce の Connected App から Salesforce REST API を使用して、 Salesforce アカウントと接続します。 OAuthパラメータ、コンシューマー・キー、およびコンシューマー・シークレットを使用して、以下の接続を検証することができます。 IBM Process Mining と Salesforce の間の接続を検証します。 Salesforce でのConnected Appの作成については、 Create a Connected Appを参照してください。
カスタムプロセスアプリの作成
Salesforce 機会管理用のカスタムプロセスアプリの作成は、以下のステップに分かれる:
プロセスアプリの作成ウィザードにアクセスする
プロセスアプリの作成ウィザードにアクセスします:
- ホーム画面で「 Start from a process application 」タイルをクリックします。
- プロセスアプリのダッシュボードで、 プロセスアプリの作成をクリックして、 プロセスアプリの作成ウィザードを開きます。
サマリー・カードの作成
サマリーカードのステップでは、以下のステップを完了する:
Name 欄にプロセスアプリの名前 「 Salesforce Opportunities 」を入力する。
「要旨」 フィールドに、Process App に関する説明を入力します。
トグルを 「クローズド・ソース (Closed source)」 または 「オープン・ソース (Open source)」 に切り替えて、Process App ユーザーの権限を設定します。 要件に応じて、以下のいずれかのオプションを選択できます。
Process App ユーザーに 「使用」、 「表示」、 「エクスポート」、および 「複製」 の各権限を付与する場合は、トグルを 「オープン・ソース」 に切り替えます。
Process App ユーザーに 「使用」 権限と 「エクスポート」 権限のみを付与する場合は、トグルを 「クローズド・ソース」 に切り替えます。
プロセスアプリのパーミッションの詳細については、 カスタムプロセスアプリのユーザーの種類とパー ミッションを参照してください。
オプション: アイコンをカスタマイズし、サマリーカードに機能のハイライトとドキュメントリンクを追加したい場合は、 カスタマイズセクションを展開してください。 カスタマイズセクションの設定については、 サマリーカードの作成を参照してください。
「次へ」 ボタンをクリックして、 「Process App ロジックのアップロード」 ステップに進みます。
プロセスアプリのロジックをアップロードする
このステップでは、データ抽出と変換を実行するpythonファイルを提供する必要があります。 この場合、 Salesforce に接続し、データを収集し、それを IBM Process Mining. Python スクリプトの作成に役立つコードテンプレートを使用できます。 テンプレートをダウンロードするには、 テンプレートのダウンロード のリンクをクリックしてください。
以下のステップでは、 Salesforce オポチュニティー管理プロセス用の Python スクリプトの作成について詳しく説明します。
インポート・ライブラリーを定義します。
import requests import json from requests.models import PreparedRequest from process_app import ProcessAppExceptionパラメーター
contextを含むexecuteという名前のメソッドを組み込みます。def execute(context):contextパラメーターには、 Python スクリプトを書くために必要なすべてのコンテキスト情報が含まれている。Connected App で構成した OAuth パラメーターと、 Salesforce アカウント資格情報を使用して、Process App と Salesforceの間の接続をセットアップします。
# reading data from accelerator config consumerKey = config['<consumerKey>'] secret = config['<consumerSecret>'] username = config['<username>'] password = config['<password>']Process App と Salesforceの間の接続に失敗した場合の例外メッセージを定義します。
if consumerKey=='' or secret =='' or username =='' or password =='': raise ProcessAppException('configuration not valid')プロセスおよび例外の Salesforce アカウント・ログを定義します。
# login to salesforce loginParams = {'client_id': consumerKey,'client_secret': secret, 'grant_type': 'password','username':username, 'password':password} req = PreparedRequest() req.prepare_url('https://login.salesforce.com/services/oauth2/token', loginParams) loginResponse = requests.post(req.url) if loginResponse.status_code != 200 : raise ProcessAppException('cannot log to salesforce account') data = loginResponse.json() accessToken = data.get('access_token') instanceUrl = data.get('instance_url')抽出する必要があるイベント・ログを定義します。
events = [] importOpportunityCreation(accessToken, instanceUrl, events) importOpportunityChange(accessToken, instanceUrl, events)抽出されたデータで返す必要があるイベント属性を定義します。
df = pd.DataFrame(events, columns= ['opportunityId', 'activity', 'startTime', 'resource', 'opportunityAmount', 'opportunityStage']) return dfSalesforce で SOQL 照会を定義してデータを抽出します。
def runSOQLQuery(query, accessToken, instanceUrl, nextRecordsUrl=None): req = PreparedRequest() if nextRecordsUrl != None: req.prepare_url(instanceUrl+nextRecordsUrl, {} ) else: req.prepare_url(instanceUrl+'/services/data/v39.0/query/', {'q' : query}) queryResponse = requests.get(req.url, headers={'Authorization': 'Bearer ' + accessToken}) if queryResponse.status_code != 200 : raise Exception('cannot perform SOQL query to salesforce account') return queryResponse.json()OpportunityCreationのデータ・テーブルを抽出して変換するための SOQL 照会を定義します。def formatDate(date): return date[0: date.find('.')].replace('T', ' ') def importOpportunityCreation(accessToken, instanceUrl, events, nextRecordsUrl=None): queryResults = runSOQLQuery('Select Id, Amount, StageName, CreatedBy.Name from Opportunity ', accessToken, instanceUrl, nextRecordsUrl) records = queryResults.get('records') for record in records: resource = record.get('CreatedBy').get('Name') createDate = formatDate(record.get('CreatedDate')) amount = record.get('Amount') events.append([ record.get('Id'),'Create Opportunity', createDate, resource, '0' if 'null' == amount else amount, record.get('StageName') ]) if queryResults.get('nextRecordsUrl') != None : importOpportunityCreation(accessToken, instanceUrl, events, queryResults.get('nextRecordsUrl'))OpportunityChangeのデータ・テーブルを抽出して変換するための SOQL 照会を定義します。def importOpportunityChange(accessToken, instanceUrl, events, nextRecordsUrl=None): queryResults = runSOQLQuery('Select OpportunityId, CreatedBy.Name, CreatedDate,' + ' Field, NewValue, OldValue from OpportunityFieldHistory', accessToken, instanceUrl, nextRecordsUrl) records = queryResults.get('records') for record in records: resource = record.get('CreatedBy').get('Name') opportunityId = record.get('OpportunityId') createDate = formatDate(record.get('CreatedDate')) field = record.get('Field') if 'StageName' == field: activity='Set Opportunity to ' + record.get('NewValue') elif 'Owner' == field: activity='Change opportunity Owner' elif 'AccountId' == field: activity = 'Change opportunity Account' elif 'Amount' == field: activity= 'Change opportunity Amount' events.append([ opportunityId, activity, createDate, resource, 0, ‘’ ]) if queryResults.get('nextRecordsUrl') != None : importOpportunityChange(accessToken, instanceUrl, events, queryResults.get('nextRecordsUrl'))
完全な Python スクリプトを含む以下のコード・スニペットをコピーして使用できます。
import requests
import json
from requests.models import PreparedRequest
from process_app import ProcessAppException
def execute(config):
# reading data from accelerator config
consumerKey = config['consumerKey']
secret = config['consumerSecret']
username = config['username']
password = config['password']
if consumerKey=='' or secret =='' or username =='' or password =='':
raise ProcessAppException('configuration not valid')
# login to salesforce
loginParams = {'client_id': consumerKey,'client_secret': secret,'grant_type': 'password','username':username,'password':password}
req = PreparedRequest()
req.prepare_url('https://login.salesforce.com/services/oauth2/token', loginParams)
loginResponse = requests.post(req.url)
if loginResponse.status_code != 200 :
raise ProcessAppException('cannot log to salesforce account')
data = loginResponse.json()
accessToken = data.get('access_token')
instanceUrl = data.get('instance_url')
events = []
importOpportunityCreation(accessToken, instanceUrl, events)
importOpportunityChange(accessToken, instanceUrl, events)
df = pd.DataFrame(events,columns= ['opportunityId', 'activity', 'startTime', 'resource',
'opportunityAmount', 'opportunityStage'])
return df
# SOQL query to extract data
def runSOQLQuery(query, accessToken, instanceUrl, nextRecordsUrl=None):
req = PreparedRequest()
if nextRecordsUrl != None:
req.prepare_url(instanceUrl+nextRecordsUrl, {} )
else:
req.prepare_url(instanceUrl+'/services/data/v39.0/query/', {'q' : query})
queryResponse = requests.get(req.url,
headers={'Authorization': 'Bearer ' + accessToken})
if queryResponse.status_code != 200 :
raise Exception('cannot perform SOQL query to salesforce account')
return queryResponse.json()
# retrieve data for opportunity creation
def formatDate(date):
return date[0: date.find('.')].replace('T', ' ')
def importOpportunityCreation(accessToken, instanceUrl, events, nextRecordsUrl=None):
queryResults = runSOQLQuery('Select Id, Amount, StageName, CreatedBy.Name from Opportunity ', accessToken, instanceUrl, nextRecordsUrl)
records = queryResults.get('records')
for record in records:
resource = record.get('CreatedBy').get('Name')
createDate = formatDate(record.get('CreatedDate'))
amount = record.get('Amount')
events.append([ record.get('Id'),'Create Opportunity', createDate, resource, '0' if 'null' == amount else amount, record.get('StageName') ])
if queryResults.get('nextRecordsUrl') != None :
importOpportunityCreation(accessToken, instanceUrl, events, queryResults.get('nextRecordsUrl'))
# retrieve data for opportunity change
def importOpportunityChange(accessToken, instanceUrl, events, nextRecordsUrl=None):
queryResults = runSOQLQuery('Select OpportunityId, CreatedBy.Name, CreatedDate,' + ' Field, NewValue, OldValue from OpportunityFieldHistory', accessToken, instanceUrl, nextRecordsUrl)
records = queryResults.get('records')
for record in records:
resource = record.get('CreatedBy').get('Name')
opportunityId = record.get('OpportunityId')
createDate = formatDate(record.get('CreatedDate'))
field = record.get('Field')
if 'StageName' == field:
activity='Set Opportunity to ' + record.get('NewValue')
elif 'Owner' == field:
activity='Change opportunity Owner'
elif 'AccountId' == field:
activity = 'Change opportunity Account'
elif 'Amount' == field:
activity= 'Change opportunity Amount'
events.append([ opportunityId, activity, createDate, resource, 0, ‘’ ])
if queryResults.get('nextRecordsUrl') != None :
importOpportunityChange(accessToken, instanceUrl, events,
queryResults.get('nextRecordsUrl'))
スクリプトを作成し、 Python ファイル(.py ファイル)をシステムに保存したら、[ Upload your Process App logic ]ステップの[ Drag and drop file here to click to upload] リンクをクリックし、[ Custom process app] ウィザードで Python ファイルを選択してアップロードします。
Python ファイルのアップロードが完了したら、 [次へ] ボタンをクリックして、 カスタムプロセスアプリウィザードの [ ユーザー入力の定義 ] ステップに進みます。
ユーザー入力の定義
「ユーザー入力の定義」 ステップでは、Process App ユーザーがプロセス生成中に変換するデータを指定するために使用する必要がある入力データ・フィールドをセットアップします。 このステップはオプションです。 ユーザー入力の定義ステップの詳細については、 ユーザー入力フィールドの定義を参照してください。
「次へ」 ボタンをクリックして、 「ユーザー・ガイダンスの提供」 ステップに進みます。
ユーザー・ガイダンスの提供
「ユーザー・ガイドの提供」 ステップでは、カスタム Process App のユーザー・ガイドを作成します。 このステップはオプションです。 ユーザーガイダンスの提供ステップの詳細については、 プロセスアプリのユーザーガイダンスの提供を参照してください。
「次へ」 ボタンをクリックして、 「プロセス設定」 ステップに進みます。
Process App のプロセスをセットアップします。
「プロセス設定」 ステップは、Process App 作成の最後のステップです。 このステップでは、 .idp 形式のプロセス・バックアップ・ファイルをアップロードするか、既存のプロセスから設定を複製して IBM Process Mining. Process App は、マップされたデータ列、プロセス設定、フィルター、およびプロセス・バックアップ・ファイルのダッシュボードを使用して、新規プロセスを生成します。
プロセス・バック・ファイルをアップロードするには、以下の手順に従います:
「プロセス設定」 ステップで 「プロセス・バックアップ・ファイルのアップロード」 オプションを選択します。
プロセス・バックアップ・ファイルをアップロードするには、 「ファイルをここにドラッグ・アンド・ドロップするか、クリックしてアップロードします」 リンクをクリックします。
「保存」ボタンをクリックします。
既存のプロセスの設定を複製するには、以下の手順を実行します。
「プロセス設定」 ステップで 「プロセスから設定を複製」 オプションを選択します。
「プロセスの検索」 ドロップダウンからプロセスを選択します。
「作成」 ボタンをクリックします。
プロセス・バックアップ・ファイルがない場合は、抽出された列 ( opportunityId、 activity、 startTime、 resource、 opportunityAmount、および opportunityStage) を使用して .csv ファイルを作成できます。 .csv 。 IBM Process Mining で、 .idp 形式のバックアップ・ファイルを作成することができる。
結果
カスタムプロセスアプリの作成が完了すると、 プロセスアプリダッシュボードに Salesforce 機会プロセスアプリが表示されます。 これで、プロセスアプリを使って IBM Process Mining.