こんにちは。torippy1024です。
前の記事の続きです。
今回は、Splunk SOAR Community Editionを使って、実際にプレイブックを作成して実行するラボを実行し、どのような処理を自動化できるのか試してみます。
ラボ実行中に、Appをインストールする作業があります。
この際、Splunkアカウントで認証する必要があるため、まだの人は作成しておいてください。
https://www.splunk.com/ja_jp/form/sign-up.html
ラボの構成
今回のラボの構成は以下の通りです。
SOARサーバー上にモックWebサーバーアプリを配置します。
このモックWebサーバーは3つのEndpointを持ち、以下の3つの機能をモックとして提供します。
(1)正常性の確認/(2)危険なIPアドレスの判定/(3)特定のIPアドレスに対するブロックです。
このモックwebサーバーに対し、SOAR上にインストールしたHTTP Appを使って通信するという構成です。
ラボの手順
STEP0 ラボアプリの準備
最初に、SOAR自身にラボアプリを用意しておきます。こちらは自作のモックアプリです。
このラボアプリがIPアドレスに対する問い合わせエンドポイント(/intel/ip/<IP Address>)と、ブロックエンドポイント(/containment/block-ip)のモックを提供しています。
vi /tmp/soar-mock-app.py
# (以下のsoar-mock-app.pyコードをコピペして保存)
#!/usr/bin/env python3
import json
import socket
from http.server import BaseHTTPRequestHandler, ThreadingHTTPServer
def route(path):
if path == "/health":
return {"status": "ok"}
if path.startswith("/intel/ip/"):
return {"verdict": "malicious" if path.endswith("/192.0.2.10") else "unknown"}
if path == "/containment/block-ip":
return {"result": "simulated"}
return None
class Handler(BaseHTTPRequestHandler):
def respond(self):
self.rfile.read(int(self.headers.get("Content-Length", 0)))
payload = route(self.path)
body = json.dumps(payload or {"error": "not found"}).encode()
self.send_response(200 if payload else 404)
self.send_header("Content-Type", "application/json")
self.send_header("Content-Length", str(len(body)))
self.end_headers()
self.wfile.write(body)
do_GET = do_POST = respond
host = socket.gethostbyname(socket.gethostname())
print("mock-api listening on http://%s:8080" % host, flush=True)
ThreadingHTTPServer((host, 8080), Handler).serve_forever()
soar-mock-app.pyの保存と実行(ラボ実行中、soar-mock-app.pyは実行したままにしておいてください。停止するときは単純にCtrl + Cで停止すればOKです)
sudo install -o soar -g soar -d /home/soar/mock-api
sudo install -o soar -g soar -m 644 /tmp/soar-mock-app.py /home/soar/mock-api/soar-mock-app.py
su - soar
python3 /home/soar/mock-api/soar-mock-app.py
# 'mock-api listening on http://<private ip>:8080'と表示されることを確認。以後、ラボが終わるまでこのターミナルは放置
別ターミナルで開いて実行確認(<private_ip>は、soar-mock-app.py実行時に表示されたIPアドレスに変更。同一ホスト内の通信であるため、8080ポートは解放しなくても通信可能です)
curl -sS http://<private_ip>:8080/health
# '{"status": "ok"}'と表示されることを確認
curl -sS http://<private_ip>:8080/intel/ip/192.0.2.10
# '{"verdict": "malicious"}'と表示されることを確認
curl -sS http://<private_ip>:8080/intel/ip/192.0.2.80
# '{"verdict": "unknown"}'と表示されることを確認
curl -sS http://<private_ip>:8080/containment/block-ip
# '{"result": "simulated"}'と表示されることを確認
STEP1 サンプルイベント作成(GUI/API)
Labelの追加
最初にイベントのLabelを作成しておきます。これは、コンテナに対して付与する属性です。
PlaybookをActivateして自動実行させる際、このLabelを条件にPlaybookを実行させるため、最初にlabラベルを付与しておきます。
- SOARにブラウザからログイン(https://<public_ip>:8443を指定)
- 画面左上のメニューから「Administration」を選択
- 「Event Settings」を選択
- 「Label Settings」を選択。最初はeventsというラベルのみが存在している
- 「+Label」ボタンを選択し、「Label name」にlabを入力して保存
ラベル一覧にlabラベルが登録されていれば完了です。
サンプルイベントの作成(GUI)
- メニューから「Events」-「My Events」を選択
- 「+Event」を選択
- 「Advanced」を選択してウインドウを拡大し、次を入力して保存
| 項目 | 値 |
|---|---|
| Name | lab-malicious-event-manual |
| Label | lab |
| Severity | medium |
4 . 作成した「lab-malicious-event-manual」イベントを選択して開き、画面右上の「View」をSummaryからAnalystに変更
5 . 「+ARTIFACT」を選択し、次を入力して保存。
| 項目 | 値 |
|---|---|
| Name | suspicious-ip |
| Label | event |
| CEF Name | sourceAddress |
| CEF Value | 192.0.2.10 |
| CEF Data Type | ip |
同様の手順を繰り返し、もう一つイベントとアーティファクトをそれぞれ追加します。
こちらは安全なIPアドレスからのイベントという設定です。
安全なIPからのイベント
| 項目 | 値 |
|---|---|
| Name | lab-clean-event-manual |
| Label | lab |
| Severity | medium |
安全なIPからのイベントに追加するアーティファクト
| 項目 | 値 |
|---|---|
| Name | clean-ip |
| Label | event |
| CEF Name | sourceAddress |
| CEF Value | 192.0.2.80 |
| CEF Data Type | ip |
サンプルイベントの作成(API)
上記はAPIから追加することも可能です。こちらは必須ではないのですが、PlaybookをActivateした際のテスト時に使うことも多いのでAPI経由の登録も試しておきます。
まず、APIを実行するためのトークンを取得します。
- メニューから「Administration」を選択
- 「User Management」-「Users」を選択
- 「Automation」ユーザーを選択し「Authentication Configuration for REST API」の右横に表示されている「Show Token」を選択しトークン値を表示
- 「Copy to Clipboard」を選択し、「ph-auth-token」をコピー
以下がコマンドのサンプルです。デフォルトだとトークンの許可IPアドレスがSOARサーバーのみに限定されているため、SOARサーバー上で実行してください。
# 怪しいIPアドレスからのイベント登録コマンド
export SOAR_AUTH_TOKEN="<ph-auth-token>"
curl -sk https://127.0.0.1:8443/rest/container -H "ph-auth-token: $SOAR_AUTH_TOKEN" -H "Content-Type: application/json" -d '{"name":"lab-malicious-event-api","label":"lab","artifacts":[{"name":"suspicious-ip","label":"event","cef":{"sourceAddress":"192.0.2.10"}}]}'
# '{"success": true, "artifacts": [{"success": true, "id": 3}], "id": 3, "new_artifact_ids": []}'などと表示されることを確認
# 安全なIPアドレスからのイベント登録コマンド
export SOAR_AUTH_TOKEN="<ph-auth-token>"
curl -sk https://127.0.0.1:8443/rest/container -H "ph-auth-token: $SOAR_AUTH_TOKEN" -H "Content-Type: application/json" -d '{"name":"lab-clean-event-api","label":"lab","artifacts":[{"name":"clean-ip","label":"event","cef":{"sourceAddress":"192.0.2.80"}}]}'
# '{"success": true, "artifacts": [{"success": true, "id": 4}], "id": 4, "new_artifact_ids": []}'などと表示されることを確認
APIで登録したイベントにはオーナーが設定されていないため、「Events」-「My Events」ではなく「Event」画面で登録されているイベント一覧を表示させてください。怪しいアドレス/安全なアドレスについて、それぞれmanual/APIで2通り、合計4つのイベントが登録されていれば完了です。
STEP2 AppとAssetの構成
次に、ラボで使用するHTTP Appをインストールし、HTTP AppのAssetを構成します。
HTTP Appのインストール
- メニューから「Apps」を選択
- 画面左上の「New Apps」を選択
- サーチバーで「HTTP」を検索(Getting new apps...という表示が消えるまで待つ)
- 「HTTP」Appが表示されたら「Install」を選択(Splunkアカウントによる認証が求められるのでユーザー名とパスワードを入力)
- インストールが完了したら「Close」を選択し、Apps一覧に「HTTP」Appが表示されていることを確認
HTTP AppのAssetの作成
Assetが作成されていないため、HTTP Appは「Unconfigured Apps」となっています。
Appに対してパラメータを指定してAssetを構成します。
- HTTP Appの「Configure New Asset」を選択
- 以下を指定して保存(base_urlのIPアドレスはprivate_ipに変更すること)
| 項目 | 値 |
|---|---|
| Asset name | lab_mock_http |
| base_url | http://<private_ip>:8080 |
| Endpoint for test connectivity | /health |
| HTTP Method for Test Connectivity | GET |
3 .「Test Connectivity」を実行
/healthエンドポイントからステータスコード200が返ってきており、Test Connectivity Passedと表示されればAssetは適切に構成されています。
STEP3 単純なPlaybookの作成
次に、イベントに対してステータス変更とコメント追加だけを行う単純なPlaybookを作成し、実行してみます。
Playbookの作成はGUIで行います。
文章で説明することは難しいので、画面キャプチャを見ながら操作してみてください。
(バージョンによって表示が少し異なるので注意が必要ですが)
Playbookの作成
- メニューから「Playbooks」を選択
- 「+playbook」を選択
- 「Select a Playbook Type」に対して「Automation」を選択
- 画面左上のPlaybook名に「lab_comment_and_status」を入力
- 画面右上のギアアイコンを選択し「Playbook Settings」メニューを表示
- 「Operates on」に「lab」を指定して「×」をクリックして「Playbook Settings」メニューを非表示にする
- 画面中央のキャンバスにある「Start」と「End」の間に、画面左にある「Utility」ブロックをドラッグアンドドロップで追加
- タブでAPIsを選択。以下の二つのActionを追加(+Utilityを選択することでActionを追加できる)
| 項目 | 値 |
|---|---|
| Action | add comment |
| comment * | lab debugger run |
| Action | set status |
| status * | closed |
9 . 「apply」を選択して「Utility」ブロックを保存
10 . 「Start」をクリックしたままドラッグして「Utility」ブロックまで矢印をつなげ、次に「Utility」ブロックをクリックしたままドラッグして「End」まで矢印をつなげる
11 .「Save」を選択してPlaybookを保存。リポジトリーとコメントは以下を指定。
| 項目 | 値 |
|---|---|
| Repo to save to | local |
| Please enter a comment (required) | lab playbook |
| Reuse this comment until editor is reloaded (Ctrl + Save or Shift + Save button to show this dialog again) | オン(トグルを右側に移動) |
Playbookの実行
1.「Data preview」パネルから「lab-malicious-event-manual」を選択し、「Save and run」を選択して実行
2 .「Debugger」タブの末尾のログに「*** Playbook 'local/lab_comment_and_status' execution (1) has completed with status: SUCCESS ***」等と表示されることを確認
メニューから「Event」を選択し、「lab-malicious-event-manual」
イベントを選択し、Status=closedとなり、soar_local_adminのコメントに「lab debugger run」が追加されていれば、無事にPlaybookが作成し処理が完了できています。
STEP4 判定/自動処理を含むPlaybookの作成
次に、IPアドレスの判定と自動処理(問い合わせ結果がverdict=maliciousだった場合には、承認ポップアップを表示し、承認されるとそのIPをブロックした旨のメッセージを表示)をさせるPlaybookを作成してみます。
ちょっと長いGUI操作になりますが、分岐も含まれるSOARらしいPlaybookになるため、ぜひやってみましょう。
Playbookの作成
- メニューから「Playbooks」を選択
- 「+playbook」を選択
- 「Select a Playbook Type」に対して「Automation」を選択
- 画面左上のPlaybook名に「lab_ip_review」を入力
- 画面右上のギアアイコンを選択し「Playbook Settings」メニューを表示
- 「Operates on」に「lab」を指定して「×」をクリックして「Playbook Settings」メニューを非表示にする
- 画面中央のキャンバスにある「Start」と「End」の間に、画面左にある「Action」ブロックをドラッグアンドドロップで追加
- タブでBy Appを選択し、HTTP Appを選択し以下を指定して「Apply」を選択。
| 項目 | 値 |
|---|---|
| HTTP App | get data |
| Asset | lab_mock_http |
| location *(※画面左の{0}アイコンをクリックしFormatted Input表示してから値を入力) | /intel/ip/{0} |
| location - Parameters | artifact:*.cef.sourceAddress |
9 .上記の「Action」ブロックの下に「Decision」ブロックを追加し、以下を入力して「Apply」を選択
| 項目 | 値 |
|---|---|
| If - Select Parameter | get_data_1:action_result.data.*.response_body.verdict |
| If - Operator | == |
| If - Select Value | malicious |
| Else | (「+Else」ボタンを押してCondition 2を追加するのみで特に指定しない) |
DecisionブロックからはCondition 1/ifとCondition 2/elseの二つの矢印を伸ばすことが可能になります。
10 .「Decision」ブロックの下(Condition 1/if側)に、「Prompt」ブロックを追加し、以下を入力して「Apply」を選択
| 項目 | 値 |
|---|---|
| Recipients | Splunk SOAR users |
| User or role* | soar_local_admin |
| Introductory message* | Mock containment requested for the source IP. |
| + Question - Question 1 | Approve mock containment ? |
| Response type | Yes/No |
| Required | チェックを入れる |
※Promptブロックは、画面上に承認可否をプロンプト表示させることができるブロックです。本来は回答によって処理内容を変化させるべきなのですが、本ラボではYes/Noどちらを選択しても処理は変えず、そのまま処理を実行させる仕様にしています。
- 「Prompt」ブロックの下に、「Action」ブロックを追加し、タブでBy Appを選択し、HTTP Appを選択。以下を指定。
| 項目 | 値 |
|---|---|
| HTTP App | post data |
| Asset | lab_mock_http |
| location *(※画面左の{0}アイコンをクリックしFormatted Input表示してから値を入力) | /containment/block-ip |
| body *(※画面左の{0}アイコンをクリックしFormatted Input表示してから値を入力) | {{"ip": "{0}"}} |
| body - Parameters | artifact:*.cef.sourceAddress |
| headers | {"Content-Type":"application/json"} |
12 .「Action」ブロックの下に「Utility」ブロックを追加し、タブでAPIsを選択。以下の二つのActionを追加
| 項目 | 値 |
|---|---|
| Action | add comment |
| comment * | mock containment requested |
| Action | set status |
| status * | closed |
13 「decision」ブロックの横(Condition 2/else側)に「Utility」ブロックを追加し、タブでAPIsを選択。以下の二つのActionを追加
| 項目 | 値 |
|---|---|
| Action | add comment |
| comment * | no malicious verdict; no containment |
| Action | set status |
| status * | closed |
14 . StartからEndまで矢印をそれぞれ接続する。Decisionブロックのみ、Condition 1(if)とCondition 2(else)の二つの矢印を接続する。好みで、ブロックを見やすい位置に移動。以下のように表示されれば完了。
15 .「Save」を選択してPlaybookを保存。リポジトリーとコメントは以下を指定。
| 項目 | 値 |
|---|---|
| Repo to save to | local |
| Please enter a comment (required) | lab playbook |
| Reuse this comment until editor is reloaded (Ctrl + Save or Shift + Save button to show this dialog again) | オン(トグルを右側に移動) |
Playbookの実行
1.「Data preview」パネル上部より「lab-malicious-event-manual」を選択し、「Save and run」を選択して実行
2 .「Debugger」タブのログに「Request sent for prompt 'prompt_1' to user 'root@localhost'」等と表示されることを確認(エラーとなる場合は、ラボの最初に起動したsoar-mock-app.pyが停止していないか確認してください)
3. ブラウザの別タブでSOAR画面を表示すると、通知アイコンが表示される。選択し、「Approve mock containment ?」に対し、Yesを選択する。

4.「Debugger」タブの末尾のログに「*** Playbook 'local/lab_ip_review' execution (4) has completed with status: SUCCESS ***」等と表示されることを確認
5 . 次に、「Data preview」パネル上部より「lab-clean-event-manual」を選択し、「Save and run」を選択して実行
6 . こちらはプロンプトが表示されず、「Debugger」タブの末尾のログに「*** Playbook 'local/lab_ip_review' execution (5) has completed with status: SUCCESS ***」等と表示されることを確認
メニューからEventを選択し、「lab-malicious-event-manual」と「lab-clean-event-manual」それぞれに対して、Analystビューより、Status=closedとなり、コメントが意図した通りに変更されていることが確認できれば、無事にPlaybookが作成し処理が完了できています。
「lab-malicious-event-api」と「lab-clean-event-api」に対して実行し、同様の結果となることを確認してもかまいません。
STEP5 PlaybookをActivate(イベント登録時に自動実行するよう構成)
最後に、Playbookを自動実行するよう構成します。
- メニューより「Playbooks」-「Internal repositories」から「lab_ip_review」を選択
- 画面右上のギアアイコンを選択し「Playbook Settings」メニューを表示
- 「Active」トグルをオンにし、「Operates on」に「lab」が指定されていることを確認して保存
以下コマンドをSOAR上で実行し、同様にプロンプトが表示され、回答を入力するとステータスがクローズになることを確認(192.0.2.10以外のIPアドレスで実行すれば、プロンプトなしでクローズされます)
export SOAR_AUTH_TOKEN="<ph-auth-token>"
curl -sk https://127.0.0.1:8443/rest/container -H "ph-auth-token: $SOAR_AUTH_TOKEN" -H "Content-Type: application/json" -d '{"name":"lab-malicious-event-active-playbook","label":"lab","artifacts":[{"name":"suspicious-ip","label":"event","cef":{"sourceAddress":"192.0.2.10"}}]}'
STEP3/STEP4がうまくいかない/面倒くさい方向け
以下にPlaybookのtgzファイルを保管しました。メニューより「Playbooks」-「Inport Playbook」アイコンを選択してそれぞれのtgzファイルをアップロードすればPlaybookの動作確認が可能です。
- lab_comment_and_status.tgz
- lab_ip_review.tgz
アップロード後、必要に応じてSTEP5を実行してください。
またSTEP0-STEP2が完了していないと、ラベルやAppが存在していないため動作しないことに注意してください。
まとめ
というわけで、Splunk SOAR Community Editionを使ってSOARを構築し、簡単なPlaybookの作成と実行を試してみました。
今回のラボではCaseの利用や、Splunkからのアラートの転送などは実行していませんが、なんとなくSplunk SOARがどのようなものか、感じ取ってもらえれば幸いです。
ざっとですが、他にSOARを学ぶ上で必要となりそうな事項としては以下があると思われます。こちらについては、どこかで機会があればまた記事を書こうと思います。
- Caseのエスカレーションと管理
- Splunk Enterprise/Cloudからのイベント転送
参考資料
Use playbooks to automate analyst workflows in Splunk SOAR (On-premises)
https://help.splunk.com/en/splunk-soar/soar-on-premises/build-playbooks/8.7.0/introduction-to-splunk-soar-on-premises-playbooks/use-playbooks-to-automate-analyst-workflows-in-splunk-soar-on-premises
Automate responses with Splunk Enterprise Security playbook blocks
https://help.splunk.com/en/splunk-soar/soar-on-premises/build-playbooks/8.7.0/use-the-playbook-editor-to-create-and-view-playbooks-to-automate-analyst-workflows/automate-responses-with-splunk-enterprise-security-playbook-blocks
About Splunk SOAR (On-premises) playbook automation APIs
https://help.splunk.com/en/splunk-soar/soar-on-premises/python-playbook-api-reference/8.7.0/overview/about-splunk-soar-on-premises-playbook-automation-apis





















