一覧SP-02-4 · EDR:端末の観測・検知・対応

EDRの収集状況と操作権限

端末、中央記録、対応処理を照合し、記録から言える範囲を判断します。

説明

イベントが見つからない理由には、活動がなかった場合のほか、センサーの停止、収集設定、除外、転送の遅延があります。権限不足も検索や対応の結果に影響します。

端末台帳と収集設定をSQLで点検します。最後に、SQLiteの読取り専用接続を使い、閲覧できることと変更できることの違いを実際に確かめます。

端末、中央記録、対応処理を照合し、記録から言える範囲を判断します。

1最終通信からの経過時間を求める

現在を100秒として確認します。

from sp02 import * db = connect() show最終通信からの経過時間を求める(db,"SELECT host,last_seen,100-last_seen AS silent_seconds,network_enabled FROM sensor ORDER BY host")

ws8は60秒通信がありません。さらにnetwork_enabledは0です。接続イベントの不在だけを正常の証拠にできません。

2監視候補を抽出する

最終通信から30秒を超えた端末です。

show監視候補を抽出する(db,"SELECT host FROM sensor WHERE 100-last_seen>30 ORDER BY host")

ws8が該当します。30秒は今回の教材の監視条件で、製品共通の正常・異常境界ではありません。

3除外の対象を確認する

除外台帳のパスを開きます。

show除外の対象を確認する(db,"SELECT host,path FROM exclusion")

ws7のC:/Temp/が対象です。除外の意味は製品や収集機能ごとに異なるため、全イベントが消えるという扱いにはしません。

4設定変更後の台帳を比較する

教材用台帳でネットワーク収集を有効へ変えます。

db.execute("UPDATE sensor SET network_enabled=1 WHERE host='ws8'") show設定変更後の台帳を比較する(db,"SELECT host,last_seen,network_enabled FROM sensor WHERE host='ws8'")

設定値は1になっても最終通信は40秒のままです。設定保存からセンサーの適用完了までは確認できません。

5閲覧と対応の権限表を確認する

役割ごとに許される操作を表示します。

show閲覧と対応の権限表を確認する(db,"SELECT role,action FROM permission ORDER BY role,action")

readerにはqueryだけ、responderにはisolateもあります。これは教材用の役割表です。実製品ではテナントや端末範囲も確認します。

6読取り専用の接続で検索する

SQLite接続をquery_onlyへ変更します。

db.execute("PRAGMA query_only=ON") show読取り専用の接続で検索する(db,"SELECT host,last_seen FROM sensor ORDER BY host")

検索は成功します。次に同じ接続で書込みを試します。

7書込み時の拒否を確認する

最終通信を現在時刻へ書き換えようとします。

try: db.execute書込み時の拒否を確認する("UPDATE sensor SET last_seen=100") except sqlite3.OperationalError as e: print(type(e).__name__,str(e)) show(db,"SELECT host,last_seen FROM sensor ORDER BY host")

readonlyのエラーで値は変わりません。このSQLの権限制御はEDRのAPI権限を検証したものではありませんが、閲覧成功と対応権限を切り分けて確認する手順は同じです。

まとめ

記録の不在は収集状態と組み合わせて判断します。

設定値と端末への適用状態を照合します。

閲覧と変更の権限をそれぞれ確認します。

操作履歴と解説を振り返れます。

Python 3.15 / SQLite / 固定の端末記録

1
from sp02 import * db = connect() show(db,"SELECT host,last_seen,100-last_seen AS silent_seconds,network_enabled FROM sensor ORDER BY host")
host | last_seen | silent_seconds | network_enabled
ws7 | 90 | 10 | 1
ws8 | 40 | 60 | 0
2
show(db,"SELECT host FROM sensor WHERE 100-last_seen>30 ORDER BY host")
host
ws8
3
show(db,"SELECT host,path FROM exclusion")
host | path
ws7 | C:/Temp/
4
db.execute("UPDATE sensor SET network_enabled=1 WHERE host='ws8'") show(db,"SELECT host,last_seen,network_enabled FROM sensor WHERE host='ws8'")
host | last_seen | network_enabled
ws8 | 40 | 1
5
show(db,"SELECT role,action FROM permission ORDER BY role,action")
role | action
reader | query
responder | isolate
responder | query
6
db.execute("PRAGMA query_only=ON") show(db,"SELECT host,last_seen FROM sensor ORDER BY host")
host | last_seen
ws7 | 90
ws8 | 40
7
try: db.execute("UPDATE sensor SET last_seen=100") except sqlite3.OperationalError as e: print(type(e).__name__,str(e)) show(db,"SELECT host,last_seen FROM sensor ORDER BY host")
OperationalError attempt to write a readonly database
host | last_seen
ws7 | 90
ws8 | 40

演習完了