mirror of
https://github.com/splunk/security_content
synced 2026-06-08 17:32:49 +00:00
Merge branch 'aws_priv_escalation' of github.com:splunk/security_content into aws_priv_escalation
This commit is contained in:
@@ -82,11 +82,17 @@ jobs:
|
||||
source venv/bin/activate
|
||||
python contentctl.py --path . --verbose validate
|
||||
- run:
|
||||
name: run doc-gen
|
||||
name: generate documentation
|
||||
command: |
|
||||
cd security-content
|
||||
source venv/bin/activate
|
||||
python bin/doc-gen.py --path . --output docs -v
|
||||
python bin/doc_gen.py --path . --output docs -v
|
||||
# now generate spec docs
|
||||
sudo apt-get install -y npm -qq
|
||||
sudo npm install -g @adobe/jsonschema2md
|
||||
jsonschema2md -d spec -o docs/spec -f yaml -e spec.json -x -
|
||||
# clean up extra properties on docs
|
||||
rm -rf docs/spec/*-*.md
|
||||
|
||||
build-sources:
|
||||
executor: content-executor
|
||||
|
||||
-702
@@ -1,702 +0,0 @@
|
||||
import glob
|
||||
import yaml
|
||||
import argparse
|
||||
from os import path
|
||||
import sys
|
||||
import re
|
||||
from jinja2 import Environment, FileSystemLoader
|
||||
|
||||
|
||||
def load_objects(file_path):
|
||||
files = []
|
||||
manifest_files = path.join(path.expanduser(REPO_PATH), file_path)
|
||||
|
||||
for file in sorted(glob.glob(manifest_files)):
|
||||
files.append(load_file(file))
|
||||
|
||||
return files
|
||||
|
||||
|
||||
def load_file(file_path):
|
||||
with open(file_path, 'r') as stream:
|
||||
try:
|
||||
file = list(yaml.safe_load_all(stream))[0]
|
||||
except yaml.YAMLError as exc:
|
||||
print(exc)
|
||||
sys.exit("ERROR: reading {0}".format(file_path))
|
||||
return file
|
||||
|
||||
|
||||
def prepare_content(stories, detections):
|
||||
|
||||
# enrich stories with information from detections: data_models, mitre_ids, kill_chain_phases, nists
|
||||
sto_to_data_models = {}
|
||||
sto_to_mitre_attack_ids = {}
|
||||
sto_to_kill_chain_phases = {}
|
||||
sto_to_ciss = {}
|
||||
sto_to_nists = {}
|
||||
sto_to_det = {}
|
||||
for detection in detections:
|
||||
if 'analytic_story' in detection['tags']:
|
||||
for story in detection['tags']['analytic_story']:
|
||||
if story in sto_to_det.keys():
|
||||
sto_to_det[story].add(detection['name'])
|
||||
else:
|
||||
sto_to_det[story] = {detection['name']}
|
||||
|
||||
data_model = parse_data_models_from_search(detection['search'])
|
||||
if data_model:
|
||||
if story in sto_to_data_models.keys():
|
||||
sto_to_data_models[story].add(data_model)
|
||||
else:
|
||||
sto_to_data_models[story] = {data_model}
|
||||
|
||||
if 'mitre_attack_id' in detection['tags']:
|
||||
if story in sto_to_mitre_attack_ids.keys():
|
||||
for mitre_attack_id in detection['tags']['mitre_attack_id']:
|
||||
sto_to_mitre_attack_ids[story].add(mitre_attack_id)
|
||||
else:
|
||||
sto_to_mitre_attack_ids[story] = set(detection['tags']['mitre_attack_id'])
|
||||
|
||||
if 'kill_chain_phases' in detection['tags']:
|
||||
if story in sto_to_kill_chain_phases.keys():
|
||||
for kill_chain in detection['tags']['kill_chain_phases']:
|
||||
sto_to_kill_chain_phases[story].add(kill_chain)
|
||||
else:
|
||||
sto_to_kill_chain_phases[story] = set(detection['tags']['kill_chain_phases'])
|
||||
|
||||
if 'cis20' in detection['tags']:
|
||||
if story in sto_to_ciss.keys():
|
||||
for cis in detection['tags']['cis20']:
|
||||
sto_to_ciss[story].add(cis)
|
||||
else:
|
||||
sto_to_ciss[story] = set(detection['tags']['cis20'])
|
||||
|
||||
if 'nist' in detection['tags']:
|
||||
if story in sto_to_nists.keys():
|
||||
for nist in detection['tags']['nist']:
|
||||
sto_to_nists[story].add(nist)
|
||||
else:
|
||||
sto_to_nists[story] = set(detection['tags']['nist'])
|
||||
|
||||
for story in stories:
|
||||
story['detections'] = sorted(sto_to_det[story['name']])
|
||||
if story['name'] in sto_to_data_models:
|
||||
story['data_models'] = sorted(sto_to_data_models[story['name']])
|
||||
if story['name'] in sto_to_mitre_attack_ids:
|
||||
story['mitre_attack_ids'] = sorted(sto_to_mitre_attack_ids[story['name']])
|
||||
if story['name'] in sto_to_kill_chain_phases:
|
||||
story['kill_chain_phases'] = sorted(sto_to_kill_chain_phases[story['name']])
|
||||
if story['name'] in sto_to_ciss:
|
||||
story['ciss'] = sorted(sto_to_ciss[story['name']])
|
||||
if story['name'] in sto_to_nists:
|
||||
story['nists'] = sorted(sto_to_nists[story['name']])
|
||||
|
||||
#sort stories into categories
|
||||
categories = []
|
||||
category_names = set()
|
||||
for story in stories:
|
||||
if 'category' in story['tags']:
|
||||
category_names.add(story['tags']['category'][0])
|
||||
|
||||
for category_name in sorted(category_names):
|
||||
new_category = {}
|
||||
new_category['name'] = category_name
|
||||
new_category['stories'] = []
|
||||
categories.append(new_category)
|
||||
|
||||
for story in stories:
|
||||
for category in categories:
|
||||
if category['name'] == story['tags']['category'][0]:
|
||||
category['stories'].append(story)
|
||||
|
||||
return categories
|
||||
|
||||
|
||||
def write_splunk_docs(stories, detections, OUTPUT_DIR):
|
||||
|
||||
categories = prepare_content(stories, detections)
|
||||
|
||||
j2_env = Environment(loader=FileSystemLoader('bin/jinja2_templates'),
|
||||
trim_blocks=True)
|
||||
template = j2_env.get_template('splunk_docs_categories.j2')
|
||||
output_path = OUTPUT_DIR + "/splunk_docs_categories.wiki"
|
||||
output = template.render(categories=categories)
|
||||
with open(output_path, 'w') as f:
|
||||
f.write(output)
|
||||
|
||||
return len(stories), output_path
|
||||
|
||||
|
||||
def write_markdown_docs(stories, detections, OUTPUT_DIR):
|
||||
|
||||
categories = prepare_content(stories, detections)
|
||||
|
||||
j2_env = Environment(loader=FileSystemLoader('bin/jinja2_templates'),
|
||||
trim_blocks=True)
|
||||
template = j2_env.get_template('stories_categories.j2')
|
||||
output_path = OUTPUT_DIR + "/stories_categories.md"
|
||||
output = template.render(categories=categories)
|
||||
with open(output_path, 'w') as f:
|
||||
f.write(output)
|
||||
|
||||
return len(stories), output_path
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# function to get unique values
|
||||
def unique(list1):
|
||||
# init a null list
|
||||
unique_list = []
|
||||
# traverse for all elements
|
||||
for x in list1:
|
||||
# check if exists in unique_list or not
|
||||
if x not in unique_list:
|
||||
unique_list.append(x)
|
||||
return unique_list
|
||||
|
||||
|
||||
def process_data_metadata(obj, complete_obj, name):
|
||||
|
||||
# collect tagging
|
||||
metadata = obj['data_metadata']
|
||||
if 'data_models' in metadata:
|
||||
complete_obj[name]['data_models'] = metadata['data_models']
|
||||
if 'providing_technologies' in metadata:
|
||||
complete_obj[name]['providing_technologies'] = metadata['providing_technologies']
|
||||
if 'data_source' in metadata:
|
||||
complete_obj[name]['data_source'] = metadata['data_source']
|
||||
|
||||
if 'mappings' in obj:
|
||||
complete_obj[name]['mappings'] = obj['mappings']
|
||||
if 'fields_required' in obj:
|
||||
complete_obj[name]['entities'] = obj['fields_required']
|
||||
if 'entities' in obj:
|
||||
complete_obj[name]['entities'] = obj['entities']
|
||||
|
||||
return complete_obj
|
||||
|
||||
|
||||
def process_metadata(detections, story_name):
|
||||
# grab mappings
|
||||
mappings = dict()
|
||||
|
||||
# grab provising technologies
|
||||
providing_technologies = []
|
||||
|
||||
# grab datamodels
|
||||
data_models = []
|
||||
|
||||
# process the above for detections
|
||||
for detection_name, detection in sorted(detections.items()):
|
||||
for s in detection['stories']:
|
||||
|
||||
# check if the detection is part of this story
|
||||
if s == story_name:
|
||||
# grab providing technologies
|
||||
if 'providing_technologies' in detection:
|
||||
for pt in detection['providing_technologies']:
|
||||
providing_technologies.append(pt)
|
||||
|
||||
# grab data models
|
||||
if 'data_models' in detection:
|
||||
for dm in detection['data_models']:
|
||||
data_models.append(dm)
|
||||
|
||||
for key in detection['mappings'].keys():
|
||||
mappings[key] = list(detection['mappings'][key])
|
||||
|
||||
return mappings, providing_technologies, data_models
|
||||
|
||||
|
||||
def generate_detections(REPO_PATH, stories):
|
||||
# first we process detections
|
||||
|
||||
detections = []
|
||||
detections_manifest_files = path.join(path.expanduser(REPO_PATH), "detections/*.yml")
|
||||
for detections_manifest_file in glob.glob(detections_manifest_files):
|
||||
|
||||
# read in each detection
|
||||
with open(detections_manifest_file, 'r') as stream:
|
||||
try:
|
||||
detection = list(yaml.safe_load_all(stream))[0]
|
||||
except yaml.YAMLError as exc:
|
||||
print(exc)
|
||||
sys.exit("ERROR: reading {0}".format(detections_manifest_file))
|
||||
|
||||
detections.append(detection)
|
||||
|
||||
complete_detections = dict()
|
||||
for detection in detections:
|
||||
# lets process v1 detections
|
||||
if detection['spec_version'] == 1:
|
||||
if verbose:
|
||||
print("processing v1 detection: {0}".format(detection['search_name']))
|
||||
name = detection['search_name']
|
||||
type = 'splunk'
|
||||
description = detection['search_description']
|
||||
id = detection['search_id']
|
||||
|
||||
# grab search information
|
||||
correlation_rule = detection['correlation_rule']
|
||||
search = detection['search']
|
||||
schedule = detection['scheduling']
|
||||
earliest_time = schedule['earliest_time']
|
||||
latest_time = schedule['latest_time']
|
||||
cron = schedule['cron_schedule']
|
||||
|
||||
# grabbing entities
|
||||
entities = []
|
||||
|
||||
investigations = []
|
||||
baselines = []
|
||||
responses = []
|
||||
for story_name, story in sorted(stories.items()):
|
||||
for d in story['detections']:
|
||||
if d['name'] == name:
|
||||
if 'investigations' in story:
|
||||
investigations = story['investigations']
|
||||
if 'baselines' in story:
|
||||
baselines = story['baselines']
|
||||
|
||||
# lets process v2 detections
|
||||
if detection['spec_version'] == 2:
|
||||
if verbose:
|
||||
print("processing v2 detection: {0}".format(detection['name']))
|
||||
name = detection['name']
|
||||
id = detection['id']
|
||||
entities = detection['entities']
|
||||
description = detection['description']
|
||||
|
||||
# splunk
|
||||
if 'splunk' in detection['detect']:
|
||||
type = 'splunk'
|
||||
correlation_rule = detection['detect']['splunk']['correlation_rule']
|
||||
search = correlation_rule['search']
|
||||
earliest_time = correlation_rule['schedule']['earliest_time']
|
||||
latest_time = correlation_rule['schedule']['latest_time']
|
||||
cron = correlation_rule['schedule']['cron_schedule']
|
||||
|
||||
# uba
|
||||
if 'uba' in detection['detect']:
|
||||
uba = detection['detect']['uba']
|
||||
type = 'uba'
|
||||
search = uba['search'] = 'CONSTRUCT DETECTION SEARCH HERE'
|
||||
# earliest_time = uba['earliest_time']
|
||||
# latest_time = uba['latest_time']
|
||||
# cron = uba['cron_schedule']
|
||||
|
||||
# phantom
|
||||
if 'phantom' in detection['detect']:
|
||||
phantom = detection['detect']['phantom']
|
||||
type = 'phantom'
|
||||
search = phantom['search'] = 'CONSTRUCT DETECTION SEARCH HERE'
|
||||
# earliest_time = phantom['earliest_time']
|
||||
# latest_time = phantom['latest_time']
|
||||
# cron = phantom['cron_schedule']
|
||||
|
||||
baselines = []
|
||||
investigations = []
|
||||
responses = []
|
||||
if 'baselines' in detection:
|
||||
for b in detection['baselines']:
|
||||
baselines.append({"type": b['type'], "name": b['name']})
|
||||
if 'investigations' in detection:
|
||||
for i in detection['investigations']:
|
||||
investigations.append({"type": i['type'], "name": i['name']})
|
||||
if 'responses' in detection:
|
||||
for r in detection['responses']:
|
||||
responses.append({"type": r['type'], "name": r['name']})
|
||||
|
||||
complete_detections[name] = {}
|
||||
complete_detections[name]['detection_name'] = name
|
||||
complete_detections[name]['id'] = id
|
||||
complete_detections[name]['search'] = search
|
||||
complete_detections[name]['latest_time'] = latest_time
|
||||
complete_detections[name]['earliest_time'] = earliest_time
|
||||
complete_detections[name]['cron'] = cron
|
||||
complete_detections[name]['investigations'] = investigations
|
||||
complete_detections[name]['baselines'] = baselines
|
||||
complete_detections[name]['responses'] = responses
|
||||
complete_detections[name]['entities'] = entities
|
||||
complete_detections[name]['description'] = description
|
||||
complete_detections[name]['correlation_rule'] = correlation_rule
|
||||
complete_detections[name]['type'] = type
|
||||
complete_detections[name]['maintainers'] = detection['maintainers']
|
||||
if 'references' not in detection:
|
||||
detection['references'] = []
|
||||
complete_detections[name]['references'] = detection['references']
|
||||
if 'channel' not in detection:
|
||||
detection['channel'] = ""
|
||||
complete_detections[name]['channel'] = detection['channel']
|
||||
if 'confidence' not in detection:
|
||||
detection['confidence'] = ""
|
||||
complete_detections[name]['confidence'] = detection['confidence']
|
||||
if 'eli5' not in detection:
|
||||
detection['eli5'] = ""
|
||||
complete_detections[name]['eli5'] = detection['eli5']
|
||||
if 'how_to_implement' not in detection:
|
||||
detection['how_to_implement'] = ""
|
||||
complete_detections[name]['how_to_implement'] = detection['how_to_implement']
|
||||
if 'asset_type' not in detection:
|
||||
detection['asset_type'] = ""
|
||||
complete_detections[name]['asset_type'] = detection['asset_type']
|
||||
if 'known_false_positives' not in detection:
|
||||
detection['known_false_positives'] = ""
|
||||
complete_detections[name]['known_false_positives'] = detection['known_false_positives']
|
||||
complete_detections[name]['security_domain'] = detection['security_domain']
|
||||
complete_detections[name]['version'] = detection['version']
|
||||
complete_detections[name]['spec_version'] = detection['spec_version']
|
||||
complete_detections[name]['creation_date'] = detection['creation_date']
|
||||
# set modification date to creation of there is not one
|
||||
if 'modification_date' in detection:
|
||||
complete_detections[name]['modification_date'] = detection['modification_date']
|
||||
else:
|
||||
complete_detections[name]['modification_date'] = detection['creation_date']
|
||||
|
||||
# process its metadata
|
||||
complete_detections = process_data_metadata(detection, complete_detections, name)
|
||||
|
||||
# stories associated with the detection
|
||||
complete_detections[name]['stories'] = []
|
||||
for story_name, story in sorted(stories.items()):
|
||||
for d in story['detections']:
|
||||
if d['name'] == name:
|
||||
complete_detections[name]['stories'].append(story['story_name'])
|
||||
|
||||
# sort uniq the results
|
||||
complete_detections[name]['stories'] = sorted(set(complete_detections[name]['stories']))
|
||||
|
||||
return complete_detections
|
||||
|
||||
|
||||
def generate_stories(REPO_PATH, verbose):
|
||||
story_files = []
|
||||
story_manifest_files = path.join(path.expanduser(REPO_PATH), "stories/*.yml")
|
||||
|
||||
for story_manifest_file in glob.glob(story_manifest_files):
|
||||
|
||||
# read in each story
|
||||
with open(story_manifest_file, 'r') as stream:
|
||||
try:
|
||||
story = list(yaml.safe_load_all(stream))[0]
|
||||
except yaml.YAMLError as exc:
|
||||
print(exc)
|
||||
sys.exit("ERROR: reading {0}".format(story_manifest_file))
|
||||
|
||||
story_files.append(story)
|
||||
|
||||
# store an object with all stories and their data
|
||||
|
||||
complete_stories = dict()
|
||||
for story in story_files:
|
||||
if verbose:
|
||||
print("processing story: {0}".format(story['name']))
|
||||
# Start building the story for the use case
|
||||
name = story['name']
|
||||
complete_stories[name] = {}
|
||||
complete_stories[name]['story_name'] = name
|
||||
complete_stories[name]['id'] = story['id']
|
||||
|
||||
# grab modification date if it has one, otherwise write as creation date
|
||||
complete_stories[name]['creation_date'] = story['creation_date']
|
||||
if 'modification_date' in story:
|
||||
complete_stories[name]['modification_date'] = story['modification_date']
|
||||
|
||||
else:
|
||||
complete_stories[name]['modification_date'] = story['creation_date']
|
||||
complete_stories[name]['description'] = story['description']
|
||||
if 'references' not in story:
|
||||
story['references'] = []
|
||||
complete_stories[name]['references'] = story['references']
|
||||
complete_stories[name]['version'] = story['version']
|
||||
complete_stories[name]['narrative'] = story['narrative']
|
||||
complete_stories[name]['spec_version'] = story['spec_version']
|
||||
complete_stories[name]['maintainers'] = story['maintainers']
|
||||
|
||||
# grab searches
|
||||
if story['spec_version'] == 1:
|
||||
detections = []
|
||||
baselines = []
|
||||
investigations = []
|
||||
category = []
|
||||
|
||||
category.append(story['category'])
|
||||
|
||||
if 'detection_searches' in story['searches']:
|
||||
for d in story['searches']['detection_searches']:
|
||||
detections.append({"type": "splunk", "name": d})
|
||||
complete_stories[name]['detections'] = detections
|
||||
|
||||
# in spec v1 these are part of the story which is why we are grabbing them here
|
||||
if 'support_searches' in story['searches']:
|
||||
for b in story['searches']['support_searches']:
|
||||
baselines.append({"type": "splunk", "name": b})
|
||||
complete_stories[name]['baselines'] = baselines
|
||||
|
||||
if 'contextual_searches' in story['searches']:
|
||||
for i in story['searches']['contextual_searches']:
|
||||
investigations.append({"type": "splunk", "name": i})
|
||||
if 'investigative_searches' in story['searches']:
|
||||
for i in story['searches']['investigative_searches']:
|
||||
investigations.append({"type": "splunk", "name": i})
|
||||
complete_stories[name]['investigations'] = investigations
|
||||
|
||||
if story['spec_version'] == 2:
|
||||
detections = []
|
||||
if 'detections' in story:
|
||||
for d in story['detections']:
|
||||
detections.append({"type": d['type'], "name": d['name']})
|
||||
complete_stories[name]['detections'] = detections
|
||||
category = story['category']
|
||||
complete_stories[name]['category'] = category
|
||||
return complete_stories
|
||||
|
||||
|
||||
def write_splunk_docs_bak(stories, detections, OUTPUT_DIR):
|
||||
|
||||
paths = []
|
||||
# Create conf files from analytics stories files
|
||||
splunk_docs_output_path = OUTPUT_DIR + "/splunk_docs_categories.wiki"
|
||||
paths.append(splunk_docs_output_path)
|
||||
output_file = open(splunk_docs_output_path, 'w')
|
||||
output_file.write("= Use Case Categories=\n")
|
||||
output_file.write("The collapse...\n")
|
||||
|
||||
# calculate categories
|
||||
categories = []
|
||||
for story_name, story in sorted(stories.items()):
|
||||
c = story['category']
|
||||
categories.append(c)
|
||||
|
||||
# get a unique set of them
|
||||
categories = unique(categories)
|
||||
for c in categories:
|
||||
output_file.write("\n\n=={0}==\n".format(c[0]))
|
||||
|
||||
# iterate through every story and print it out
|
||||
for story_name, story in sorted(stories.items()):
|
||||
# if the category matches
|
||||
if story['category'] == c:
|
||||
output_file.write("\n==={0}===\n".format(story_name))
|
||||
output_file.write("\n{0}\n".format(story['description']))
|
||||
output_file.write(
|
||||
"""\n<div class="toccolours mw-collapsible">\n<div class="mw-collapsible-content">\n""")
|
||||
# header information
|
||||
output_file.write("\n====Narrative====\n{0}\n".format(story['narrative']))
|
||||
|
||||
mappings, providing_technologies, data_models = process_metadata(detections, story_name)
|
||||
|
||||
# providing tech
|
||||
output_file.write("\n====Providing Technologies====\n")
|
||||
providing_technologies = unique(providing_technologies)
|
||||
for pt in providing_technologies:
|
||||
output_file.write("* {0}\n".format(pt))
|
||||
|
||||
# providing tech
|
||||
output_file.write("\n====Data Models====\n")
|
||||
data_models = unique(data_models)
|
||||
for dm in data_models:
|
||||
output_file.write("* {0}\n".format(dm))
|
||||
|
||||
# mappings
|
||||
output_file.write("\n====Mappings====\n")
|
||||
|
||||
output_file.write("\n=====ATT&CK=====\n")
|
||||
if mappings['mitre_attack']:
|
||||
for m in mappings['mitre_attack']:
|
||||
output_file.write("* {0}\n".format(m))
|
||||
|
||||
output_file.write("\n=====Kill Chain Phases=====\n")
|
||||
if mappings['kill_chain_phases']:
|
||||
for m in mappings['kill_chain_phases']:
|
||||
output_file.write("* {0}\n".format(m))
|
||||
|
||||
if mappings['cis20']:
|
||||
output_file.write("\n=====CIS=====\n")
|
||||
for m in mappings['cis20']:
|
||||
output_file.write("* {0}\n".format(m))
|
||||
|
||||
if mappings['nist']:
|
||||
output_file.write("\n=====NIST=====\n")
|
||||
for m in mappings['nist']:
|
||||
output_file.write("* {0}\n".format(m))
|
||||
|
||||
# references
|
||||
output_file.write("\n====References====\n")
|
||||
for r in story['references']:
|
||||
output_file.write("* {0}\n".format(r))
|
||||
|
||||
# story details
|
||||
output_file.write("\ncreation_date = {0}\n\n".format(story['creation_date']))
|
||||
output_file.write("modification_date = {0}\n\n".format(story['modification_date']))
|
||||
output_file.write("version = {0}\n".format(story['version']))
|
||||
|
||||
# footer information
|
||||
output_file.write("""\n</div>\n</div>\n""")
|
||||
output_file.write("""\n[[Category:V:Lab:drafts]]""")
|
||||
|
||||
output_file.close()
|
||||
story_count = len(stories.keys())
|
||||
return story_count, paths
|
||||
|
||||
|
||||
def write_markdown_docs_bak(stories, detections, OUTPUT_DIR):
|
||||
paths = []
|
||||
# Create conf files from analytics stories files
|
||||
splunk_docs_output_path = OUTPUT_DIR + "/stories_categories.md"
|
||||
paths.append(splunk_docs_output_path)
|
||||
output_file = open(splunk_docs_output_path, 'w')
|
||||
output_file.write("# Categories\n")
|
||||
output_file.write("Analytics stories organized by categories\n")
|
||||
|
||||
# calculate categories
|
||||
categories = []
|
||||
for story_name, story in sorted(stories.items()):
|
||||
c = story['category']
|
||||
categories.append(c)
|
||||
|
||||
# get a unique set of them
|
||||
categories = unique(categories)
|
||||
|
||||
# build category TOC
|
||||
for c in categories:
|
||||
output_file.write("\n* [{0}](#{1})\n".format(c[0], c[0].replace(' ', '-').lower()))
|
||||
|
||||
for c in categories:
|
||||
output_file.write("\n\n## {0}\n".format(c[0]))
|
||||
|
||||
# build story TOC
|
||||
for story_name, story in sorted(stories.items()):
|
||||
# if the category matches
|
||||
if story['category'] == c:
|
||||
output_file.write("\n* [{0}](#{1})\n".format(story_name, story_name.replace(' ', '-').lower()))
|
||||
|
||||
# iterate through every story and print it out
|
||||
for story_name, story in sorted(stories.items()):
|
||||
# if the category matches
|
||||
if story['category'] == c:
|
||||
output_file.write("\n### {0}\n".format(story_name))
|
||||
# basic story info
|
||||
output_file.write("* id = `{0}`\n".format(story['id']))
|
||||
output_file.write("* creation_date = {0}\n".format(story['creation_date']))
|
||||
output_file.write("* modification_date = {0}\n".format(story['modification_date']))
|
||||
output_file.write("* version = {0}\n".format(story['version']))
|
||||
output_file.write("* spec_version = {0}\n".format(story['spec_version']))
|
||||
|
||||
# description and narrative
|
||||
output_file.write("\n##### Description\n{0}\n".format(story['description']))
|
||||
output_file.write("\n##### Narrative\n{0}\n".format(story['narrative']))
|
||||
|
||||
# process detections
|
||||
output_file.write("\n##### Detections\n")
|
||||
# write all detections
|
||||
if 'detections' in story:
|
||||
for d in story['detections']:
|
||||
output_file.write("* {0}\n".format(d['name']))
|
||||
|
||||
mappings, providing_technologies, data_models = process_metadata(detections, story_name)
|
||||
|
||||
# providing tech
|
||||
output_file.write("\n##### Providing Technologies\n")
|
||||
providing_technologies = unique(providing_technologies)
|
||||
for pt in providing_technologies:
|
||||
output_file.write("* {0}\n".format(pt))
|
||||
|
||||
# data models
|
||||
output_file.write("\n##### Data Models\n")
|
||||
data_models = unique(data_models)
|
||||
for dm in data_models:
|
||||
output_file.write("{0}\n".format(dm))
|
||||
|
||||
# mappings
|
||||
output_file.write("\n##### Mappings\n")
|
||||
|
||||
output_file.write("\n###### ATT&CK\n")
|
||||
if mappings['mitre_attack']:
|
||||
for m in mappings['mitre_attack']:
|
||||
output_file.write("* {0}\n".format(m))
|
||||
|
||||
output_file.write("\n###### Kill Chain Phases\n")
|
||||
if mappings['kill_chain_phases']:
|
||||
for m in mappings['kill_chain_phases']:
|
||||
output_file.write("* {0}\n".format(m))
|
||||
|
||||
if mappings['cis20']:
|
||||
output_file.write("\n###### CIS\n")
|
||||
for m in mappings['cis20']:
|
||||
output_file.write("* {0}\n".format(m))
|
||||
|
||||
if mappings['nist']:
|
||||
output_file.write("\n###### NIST\n")
|
||||
for m in mappings['nist']:
|
||||
output_file.write("* {0}\n".format(m))
|
||||
|
||||
# maintainers
|
||||
output_file.write("\n##### Maintainers\n")
|
||||
for m in story['maintainers']:
|
||||
output_file.write("* name = {0}\n".format(m['name']))
|
||||
output_file.write("* email = {0}\n".format(m['email']))
|
||||
output_file.write("* company = {0}\n".format(m['company']))
|
||||
|
||||
# references
|
||||
output_file.write("\n##### References\n")
|
||||
for r in story['references']:
|
||||
output_file.write("* {0}\n".format(r))
|
||||
|
||||
output_file.close()
|
||||
story_count = len(stories.keys())
|
||||
return story_count, paths
|
||||
|
||||
|
||||
def parse_data_models_from_search(search):
|
||||
match = re.search('from\sdatamodel\s?=\s?([^\s.]*)',search)
|
||||
if match is not None:
|
||||
return match.group(1)
|
||||
return False
|
||||
|
||||
if __name__ == "__main__":
|
||||
|
||||
# grab arguments
|
||||
parser = argparse.ArgumentParser(description="generates documentation from our content", epilog="""
|
||||
This tool converts manifests information to documents in variious format like markdown and wiki markup used by Splunk docs.""")
|
||||
parser.add_argument("-p", "--path", required=True, help="path to security_content repo")
|
||||
parser.add_argument("-o", "--output", required=True, help="path to the output directory for the docs")
|
||||
parser.add_argument("-v", "--verbose", required=False, default=False, action='store_true', help="prints verbose output")
|
||||
parser.add_argument("-gsd", "--gen_splunk_docs", required=False, default=True, action='store_true',
|
||||
help="generates wiki markup splunk documentation, default to true")
|
||||
parser.add_argument("-gmd", "--gen_markdown_docs", required=False, default=True, action='store_true',
|
||||
help="generates markdown docs, default to true")
|
||||
|
||||
# parse them
|
||||
args = parser.parse_args()
|
||||
REPO_PATH = args.path
|
||||
OUTPUT_DIR = args.output
|
||||
verbose = args.verbose
|
||||
gsd = args.gen_splunk_docs
|
||||
gmd = args.gen_markdown_docs
|
||||
|
||||
stories = load_objects("stories/*.yml")
|
||||
detections = []
|
||||
detections = load_objects("detections/*/*.yml")
|
||||
detections.extend(load_objects("detections/*/*/*.yml"))
|
||||
|
||||
# complete_stories = generate_stories(REPO_PATH, verbose)
|
||||
# complete_detections = generate_detections(REPO_PATH, complete_stories)
|
||||
|
||||
if gsd:
|
||||
story_count, path = write_splunk_docs(stories, detections, OUTPUT_DIR)
|
||||
print("{0} story documents have been successfully written to {1}".format(story_count, path))
|
||||
else:
|
||||
print("--gen_splunk_docs was set to false, not generating splunk documentation")
|
||||
|
||||
if gmd:
|
||||
story_count, path = write_markdown_docs(stories, detections, OUTPUT_DIR)
|
||||
print("{0} story documents have been successfully written to {1}".format(story_count, path))
|
||||
else:
|
||||
print("--gen_splunk_docs was set to false, not generating splunk documentation")
|
||||
|
||||
print("documentation generation for security content completed..")
|
||||
+268
@@ -0,0 +1,268 @@
|
||||
import glob
|
||||
import yaml
|
||||
import argparse
|
||||
import sys
|
||||
import re
|
||||
from os import path, walk
|
||||
import json
|
||||
from jinja2 import Environment, FileSystemLoader
|
||||
from pyattck import Attck
|
||||
|
||||
|
||||
def mitre_attack_object(technique, attack):
|
||||
mitre_attack = dict()
|
||||
mitre_attack['technique_id'] = technique.id
|
||||
mitre_attack['technique'] = technique.name
|
||||
|
||||
# process tactics
|
||||
tactics = []
|
||||
for tactic in technique.tactics:
|
||||
tactics.append(tactic.name)
|
||||
mitre_attack['tactic'] = tactics
|
||||
|
||||
return mitre_attack
|
||||
|
||||
def get_mitre_enrichment_new(attack, mitre_attack_id):
|
||||
for technique in attack.enterprise.techniques:
|
||||
apt_groups = []
|
||||
if '.' in mitre_attack_id:
|
||||
for subtechnique in technique.subtechniques:
|
||||
if mitre_attack_id == subtechnique.id:
|
||||
mitre_attack = mitre_attack_object(subtechnique, attack)
|
||||
return mitre_attack
|
||||
|
||||
elif mitre_attack_id == technique.id:
|
||||
mitre_attack = mitre_attack_object(technique, attack)
|
||||
return mitre_attack
|
||||
return []
|
||||
|
||||
def generate_doc_stories(REPO_PATH, OUTPUT_DIR, TEMPLATE_PATH, attack, sorted_detections, messages, VERBOSE):
|
||||
manifest_files = []
|
||||
for root, dirs, files in walk(REPO_PATH + '/stories'):
|
||||
for file in files:
|
||||
if file.endswith(".yml"):
|
||||
manifest_files.append((path.join(root, file)))
|
||||
|
||||
stories = []
|
||||
for manifest_file in manifest_files:
|
||||
story_yaml = dict()
|
||||
if VERBOSE:
|
||||
print("processing manifest {0}".format(manifest_file))
|
||||
|
||||
with open(manifest_file, 'r') as stream:
|
||||
try:
|
||||
object = list(yaml.safe_load_all(stream))[0]
|
||||
except yaml.YAMLError as exc:
|
||||
print(exc)
|
||||
print("Error reading {0}".format(manifest_file))
|
||||
sys.exit(1)
|
||||
story_yaml = object
|
||||
|
||||
# enrich the mitre object
|
||||
mitre_attacks = []
|
||||
if 'mitre_attack_id' in story_yaml['tags']:
|
||||
for mitre_technique_id in story_yaml['tags']['mitre_attack_id']:
|
||||
mitre_attack = get_mitre_enrichment_new(attack, mitre_technique_id)
|
||||
mitre_attacks.append(mitre_attack)
|
||||
# story_yaml['mitre_attacks'] = sorted(mitre_attacks, key = lambda i: i['tactic'])
|
||||
story_yaml['mitre_attacks'] = mitre_attacks
|
||||
stories.append(story_yaml)
|
||||
|
||||
sorted_stories = sorted(stories, key=lambda i: i['name'])
|
||||
|
||||
# enrich stories with information from detections: data_models, mitre_ids, kill_chain_phases
|
||||
sto_to_data_models = {}
|
||||
sto_to_mitre_attack_ids = {}
|
||||
sto_to_mitre_attacks = {}
|
||||
sto_to_kill_chain_phases = {}
|
||||
sto_to_det = {}
|
||||
for detection in sorted_detections:
|
||||
if 'analytic_story' in detection['tags']:
|
||||
for story in detection['tags']['analytic_story']:
|
||||
if story in sto_to_det.keys():
|
||||
sto_to_det[story].add(detection['name'])
|
||||
else:
|
||||
sto_to_det[story] = {detection['name']}
|
||||
data_model = detection['datamodel']
|
||||
if data_model:
|
||||
for d in data_model:
|
||||
if story in sto_to_data_models.keys():
|
||||
sto_to_data_models[story].add(d)
|
||||
else:
|
||||
sto_to_data_models[story] = {d}
|
||||
|
||||
if 'mitre_attack_id' in detection['tags']:
|
||||
if story in sto_to_mitre_attack_ids.keys():
|
||||
for mitre_attack_id in detection['tags']['mitre_attack_id']:
|
||||
sto_to_mitre_attack_ids[story].add(mitre_attack_id)
|
||||
else:
|
||||
sto_to_mitre_attack_ids[story] = set(detection['tags']['mitre_attack_id'])
|
||||
|
||||
if 'kill_chain_phases' in detection['tags']:
|
||||
if story in sto_to_kill_chain_phases.keys():
|
||||
for kill_chain in detection['tags']['kill_chain_phases']:
|
||||
sto_to_kill_chain_phases[story].add(kill_chain)
|
||||
else:
|
||||
sto_to_kill_chain_phases[story] = set(detection['tags']['kill_chain_phases'])
|
||||
|
||||
if 'mitre_attacks' in detection:
|
||||
if story in sto_to_mitre_attacks.keys():
|
||||
for mitre_attack in detection['mitre_attacks']:
|
||||
if mitre_attack not in sto_to_mitre_attacks[story]:
|
||||
sto_to_mitre_attacks[story].append(mitre_attack)
|
||||
else:
|
||||
sto_to_mitre_attacks[story] = detection['mitre_attacks']
|
||||
|
||||
# add the enrich objects to the story
|
||||
for story in sorted_stories:
|
||||
story['detections'] = sorted(sto_to_det[story['name']])
|
||||
if story['name'] in sto_to_data_models:
|
||||
story['data_models'] = sorted(sto_to_data_models[story['name']])
|
||||
if story['name'] in sto_to_mitre_attack_ids:
|
||||
story['mitre_attack_ids'] = sorted(sto_to_mitre_attack_ids[story['name']])
|
||||
if story['name'] in sto_to_mitre_attacks:
|
||||
story['mitre_attacks'] = sto_to_mitre_attacks[story['name']]
|
||||
if story['name'] in sto_to_kill_chain_phases:
|
||||
story['kill_chain_phases'] = sorted(sto_to_kill_chain_phases[story['name']])
|
||||
|
||||
# sort stories into categories
|
||||
categories = []
|
||||
category_names = set()
|
||||
for story in sorted_stories:
|
||||
if 'category' in story['tags']:
|
||||
category_names.add(story['tags']['category'][0])
|
||||
|
||||
for category_name in sorted(category_names):
|
||||
new_category = {}
|
||||
new_category['name'] = category_name
|
||||
new_category['stories'] = []
|
||||
categories.append(new_category)
|
||||
|
||||
for story in sorted_stories:
|
||||
for category in categories:
|
||||
if category['name'] == story['tags']['category'][0]:
|
||||
category['stories'].append(story)
|
||||
|
||||
j2_env = Environment(loader=FileSystemLoader(TEMPLATE_PATH),
|
||||
trim_blocks=False)
|
||||
# write markdown
|
||||
template = j2_env.get_template('doc_stories_markdown.j2')
|
||||
output_path = path.join(OUTPUT_DIR + '/stories.md')
|
||||
output = template.render(categories=categories)
|
||||
with open(output_path, 'w', encoding="utf-8") as f:
|
||||
f.write(output)
|
||||
messages.append("doc_gen.py wrote {0} stories documentation in markdown to: {1}".format(len(stories),output_path))
|
||||
|
||||
# write wikimarkup
|
||||
template = j2_env.get_template('doc_stories_wiki.j2')
|
||||
output_path = path.join(OUTPUT_DIR + '/stories.wiki')
|
||||
output = template.render(categories=categories)
|
||||
with open(output_path, 'w', encoding="utf-8") as f:
|
||||
f.write(output)
|
||||
messages.append("doc_gen.py wrote {0} stories documentation in mediawiki to: {1}".format(len(stories),output_path))
|
||||
return sorted_stories, messages
|
||||
|
||||
|
||||
def generate_doc_detections(REPO_PATH, OUTPUT_DIR, TEMPLATE_PATH, attack, messages, VERBOSE):
|
||||
types = ["endpoint", "application", "cloud", "network", "web", "experimental", "deprecated"]
|
||||
manifest_files = []
|
||||
for t in types:
|
||||
for root, dirs, files in walk(REPO_PATH + '/detections/' + t):
|
||||
for file in files:
|
||||
if file.endswith(".yml"):
|
||||
manifest_files.append((path.join(root, file)))
|
||||
|
||||
detections = []
|
||||
for manifest_file in manifest_files:
|
||||
detection_yaml = dict()
|
||||
if VERBOSE:
|
||||
print("processing manifest {0}".format(manifest_file))
|
||||
|
||||
with open(manifest_file, 'r') as stream:
|
||||
try:
|
||||
object = list(yaml.safe_load_all(stream))[0]
|
||||
except yaml.YAMLError as exc:
|
||||
print(exc)
|
||||
print("Error reading {0}".format(manifest_file))
|
||||
sys.exit(1)
|
||||
detection_yaml = object
|
||||
|
||||
# enrich the mitre object
|
||||
mitre_attacks = []
|
||||
if 'mitre_attack_id' in detection_yaml['tags']:
|
||||
for mitre_technique_id in detection_yaml['tags']['mitre_attack_id']:
|
||||
mitre_attack = get_mitre_enrichment_new(attack, mitre_technique_id)
|
||||
mitre_attacks.append(mitre_attack)
|
||||
detection_yaml['mitre_attacks'] = mitre_attacks
|
||||
#detection_yaml['mitre_attacks'] = sorted(mitre_attacks, key = lambda i: i['tactic'])
|
||||
detection_yaml['kind'] = manifest_file.split('/')[-2]
|
||||
detections.append(detection_yaml)
|
||||
|
||||
sorted_detections = sorted(detections, key=lambda i: i['name'])
|
||||
|
||||
j2_env = Environment(loader=FileSystemLoader(TEMPLATE_PATH),
|
||||
trim_blocks=False)
|
||||
|
||||
# write markdown
|
||||
template = j2_env.get_template('doc_detections_markdown.j2')
|
||||
output_path = path.join(OUTPUT_DIR + '/detections.md')
|
||||
output = template.render(detections=sorted_detections)
|
||||
with open(output_path, 'w', encoding="utf-8") as f:
|
||||
f.write(output)
|
||||
messages.append("doc_gen.py wrote {0} detections documentation in markdown to: {1}".format(len(detections),output_path))
|
||||
|
||||
#sort detections by kind into categories
|
||||
kinds = []
|
||||
kind_names = set()
|
||||
for detection in sorted_detections:
|
||||
kind_names.add(detection['kind'])
|
||||
|
||||
for kind_name in sorted(kind_names):
|
||||
new_kind = {}
|
||||
new_kind['name'] = kind_name
|
||||
new_kind['detections'] = []
|
||||
kinds.append(new_kind)
|
||||
|
||||
for detection in sorted_detections:
|
||||
for kind in kinds:
|
||||
if kind['name'] == detection['kind']:
|
||||
kind['detections'].append(detection)
|
||||
|
||||
# write wikimarkup
|
||||
template = j2_env.get_template('doc_detections_wiki.j2')
|
||||
output_path = path.join(OUTPUT_DIR + '/detections.wiki')
|
||||
output = template.render(kinds=kinds)
|
||||
with open(output_path, 'w', encoding="utf-8") as f:
|
||||
f.write(output)
|
||||
messages.append("doc_gen.py wrote {0} detections documentation in mediawiki to: {1}".format(len(detections),output_path))
|
||||
|
||||
return sorted_detections, messages
|
||||
if __name__ == "__main__":
|
||||
|
||||
# grab arguments
|
||||
parser = argparse.ArgumentParser(description="Generates documentation from Splunk Security Content", epilog="""
|
||||
This tool converts all Splunk Security Content detections, stories, workbooks and spec files into documentation. It builds both wiki markup (Splunk Docs) an markdown documentation.""")
|
||||
parser.add_argument("-p", "--path", required=True, help="path to security_content repo")
|
||||
parser.add_argument("-o", "--output", required=True, help="path to the output directory for the docs")
|
||||
parser.add_argument("-v", "--verbose", required=False, default=False, action='store_true', help="prints verbose output")
|
||||
|
||||
# parse them
|
||||
args = parser.parse_args()
|
||||
REPO_PATH = args.path
|
||||
OUTPUT_DIR = args.output
|
||||
VERBOSE = args.verbose
|
||||
|
||||
TEMPLATE_PATH = path.join(REPO_PATH, 'bin/jinja2_templates')
|
||||
|
||||
if VERBOSE:
|
||||
print("getting mitre enrichment data from cti")
|
||||
attack = Attck()
|
||||
|
||||
messages = []
|
||||
sorted_detections, messages = generate_doc_detections(REPO_PATH, OUTPUT_DIR, TEMPLATE_PATH, attack, messages, VERBOSE)
|
||||
sorted_stories, messages = generate_doc_stories(REPO_PATH, OUTPUT_DIR, TEMPLATE_PATH, attack, sorted_detections, messages, VERBOSE)
|
||||
|
||||
# print all the messages from generation
|
||||
for m in messages:
|
||||
print(m)
|
||||
print("finished successfully!")
|
||||
@@ -0,0 +1,124 @@
|
||||
# Splunk Security Content Detections
|
||||

|
||||
=====
|
||||
All the detections shipped to different Splunk products. Below is a breakdown by kind.
|
||||
|
||||
## Cloud
|
||||
<details>
|
||||
<summary>details</summary>
|
||||
|
||||
{% for detection in detections %}
|
||||
{% if detection.kind == 'cloud' %}
|
||||
- [{{ detection.name }}](#{{ detection.name|lower|replace(" ", "-") }})
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</details>
|
||||
|
||||
## Endpoint
|
||||
<details>
|
||||
<summary>details</summary>
|
||||
|
||||
{% for detection in detections %}
|
||||
{% if detection.kind == 'endpoint' %}
|
||||
- [{{ detection.name }}](#{{ detection.name|lower|replace(" ", "-") }})
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</details>
|
||||
|
||||
## Network
|
||||
<details>
|
||||
<summary>details</summary>
|
||||
|
||||
{% for detection in detections %}
|
||||
{% if detection.kind == 'network' %}
|
||||
- [{{ detection.name }}](#{{ detection.name|lower|replace(" ", "-") }})
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</details>
|
||||
|
||||
## Application
|
||||
<details>
|
||||
<summary>details</summary>
|
||||
|
||||
{% for detection in detections %}
|
||||
{% if detection.kind == 'application' %}
|
||||
- [{{ detection.name }}](#{{ detection.name|lower|replace(" ", "-") }})
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</details>
|
||||
|
||||
## Web
|
||||
<details>
|
||||
<summary>details</summary>
|
||||
|
||||
{% for detection in detections %}
|
||||
{% if detection.kind == 'web' %}
|
||||
- [{{ detection.name }}](#{{ detection.name|lower|replace(" ", "-") }})
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</details>
|
||||
|
||||
|
||||
|
||||
{% for detection in detections %}
|
||||
### {{ detection.name }}
|
||||
{{ detection.description }}
|
||||
|
||||
- **Product**: {{ detection.tags.product|join(', ') }}
|
||||
- **Datamodel**: {{ detection.datamodel|join(', ') }}
|
||||
- **ATT&CK**: {% for mitre_attack_id in detection.tags.mitre_attack_id %}[{{ mitre_attack_id }}](https://attack.mitre.org/techniques/{{ mitre_attack_id }}/){% if not loop.last %}, {% endif %}{% endfor %}
|
||||
- **Last Updated**: {{ detection.date }}
|
||||
|
||||
<details>
|
||||
<summary>details</summary>
|
||||
|
||||
#### Search
|
||||
```
|
||||
{{ detection.search|replace("|", "\n|") }}
|
||||
```
|
||||
#### Associated Analytic Story
|
||||
{% for story in detection.tags.analytic_story %}
|
||||
* {{ story }}
|
||||
{% endfor %}
|
||||
|
||||
#### How To Implement
|
||||
{{ detection.how_to_implement}}
|
||||
|
||||
#### Required field
|
||||
{% for field in detection.tags.required_fields %}
|
||||
* {{ field }}
|
||||
{% endfor %}
|
||||
|
||||
{% if detection.mitre_attacks %}
|
||||
#### ATT&CK
|
||||
|
||||
| ID | Technique | Tactic |
|
||||
| ----------- | ----------- |--------------|
|
||||
{%- for attack in detection.mitre_attacks %}
|
||||
| {{ attack.technique_id }} | {{ attack.technique }} | {{ attack.tactic|join(', ') }} |
|
||||
{%- endfor %}
|
||||
{% endif %}
|
||||
|
||||
#### Kill Chain Phase
|
||||
{% for phase in detection.tags.kill_chain_phases %}
|
||||
* {{ phase }}
|
||||
{% endfor %}
|
||||
|
||||
#### Known False Positives
|
||||
{{ detection.known_false_positives}}
|
||||
|
||||
#### Reference
|
||||
{% for reference in detection.references %}
|
||||
* {{ reference }}
|
||||
{% endfor %}
|
||||
|
||||
#### Test Dataset
|
||||
{% for dataset in detection.tags.dataset %}
|
||||
* {{ dataset }}
|
||||
{% endfor %}
|
||||
|
||||
_version_: {{detection.version}}
|
||||
</details>
|
||||
|
||||
---
|
||||
{% endfor %}
|
||||
@@ -0,0 +1,85 @@
|
||||
=Splunk Security Content Detections =
|
||||
|
||||
----
|
||||
All the detections shipped to different Splunk products. Below is a breakdown by kind.
|
||||
{% for kind in kinds %}
|
||||
=={{ kind.name|capitalize }}==
|
||||
|
||||
{% for detection in kind.detections %}
|
||||
==={{ detection.name|capitalize}}===
|
||||
{{ detection.description }}
|
||||
|
||||
* '''Product''': {{ detection.tags.product|join(', ') }}
|
||||
* '''Datamodel''': {{ detection.datamodel|join(', ') }}
|
||||
* '''ATT&CK''': {% for attack in detection.mitre_attacks %}[https://attack.mitre.org/techniques/{{ attack.technique_id }}/ {{ attack.technique_id }}]{% if not loop.last %}, {% endif %}{% endfor %}
|
||||
* '''Last Updated''': {{ detection.date }}
|
||||
|
||||
<div class="toccolours mw-collapsible mw-collapsed">
|
||||
<div class="mw-collapsible-content">
|
||||
|
||||
====Search====
|
||||
<search>{{ detection.search|replace("|", "\n|") }}</search>
|
||||
|
||||
====Associated Analytic Story====
|
||||
{% for story in detection.tags.analytic_story %}
|
||||
* [[Documentation:ESSOC:stories:UseCase#{{ story|replace(" ", "_") }}|{{ story }}]]
|
||||
{% endfor %}
|
||||
|
||||
====How To Implement====
|
||||
{{ detection.how_to_implement}}
|
||||
|
||||
====Required field====
|
||||
{% for field in detection.tags.required_fields %}
|
||||
* {{ field }}
|
||||
{% endfor %}
|
||||
|
||||
{% if detection.mitre_attacks|length > 0 %}
|
||||
====ATT&CK====
|
||||
{|
|
||||
! style="text-align:left;"| ID
|
||||
! Technique
|
||||
! Tactic
|
||||
{%-for attack in detection.mitre_attacks %}
|
||||
|-
|
||||
| {{ attack.technique_id }}
|
||||
| {{ attack.technique }}
|
||||
| {{ attack.tactic|join(', ') }}
|
||||
{%- endfor %}
|
||||
|}
|
||||
{% endif %}
|
||||
|
||||
====Kill Chain Phase====
|
||||
{% for phase in detection.tags.kill_chain_phases %}
|
||||
* {{ phase }}
|
||||
{% endfor %}
|
||||
|
||||
====Known False Positives====
|
||||
{{ detection.known_false_positives}}
|
||||
|
||||
====Reference====
|
||||
{% for reference in detection.references %}
|
||||
* {{ reference }}
|
||||
{% endfor %}
|
||||
|
||||
====Test Dataset====
|
||||
{% for dataset in detection.tags.dataset %}
|
||||
* {{ dataset }}
|
||||
{% endfor %}
|
||||
|
||||
''version'': {{detection.version}}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
----
|
||||
{% endfor %}
|
||||
|
||||
{% endfor %}
|
||||
|
||||
''#############''
|
||||
''# Automatically generated by doc_gen.py in https://github.com/splunk/security_content''
|
||||
''# On Date: {{ time }} UTC''
|
||||
''# Author: Splunk Security Research''
|
||||
''# Contact: research@splunk.com''
|
||||
''#############''
|
||||
|
||||
[[Category:V:ESSOC:drafts]]
|
||||
@@ -0,0 +1,51 @@
|
||||
# Splunk Security Content Analytic Stories
|
||||

|
||||
=====
|
||||
All the Analytic Stories shipped to different Splunk products. Below is a breakdown by kind.
|
||||
|
||||
{% for category in categories %}
|
||||
## {{ category.name }}
|
||||
<details>
|
||||
<summary>details</summary>
|
||||
{% for story in category.stories %}
|
||||
### {{ story.name }}
|
||||
{{ story.description }}
|
||||
|
||||
- **Product**: {{ story.tags.product|join(', ') }}
|
||||
- **Datamodel**: {{ story.data_models|join(', ') }}
|
||||
- **ATT&CK**: {% for mitre_attack_id in story.mitre_attack_ids %}[{{ mitre_attack_id }}](https://attack.mitre.org/techniques/{{ mitre_attack_id }}/){% if not loop.last %}, {% endif %}{% endfor %}
|
||||
- **Last Updated**: {{ story.date }}
|
||||
|
||||
<details>
|
||||
<summary>details</summary>
|
||||
|
||||
#### Detection Profile
|
||||
{% for detection in story.detections %}
|
||||
* [{{ detection }}](detections.md#{{ detection|lower|replace(" ", "-") }})
|
||||
{% endfor %}
|
||||
|
||||
#### ATT&CK
|
||||
|
||||
| ID | Technique | Tactic |
|
||||
| ----------- | ----------- |--------------|
|
||||
{%- for attack in story.mitre_attacks %}
|
||||
| {{ attack.technique_id }} | {{ attack.technique }} | {{ attack.tactic|join(', ') }} |
|
||||
{%- endfor %}
|
||||
|
||||
#### Kill Chain Phase
|
||||
{% for phase in story.kill_chain_phases %}
|
||||
* {{ phase }}
|
||||
{% endfor %}
|
||||
|
||||
#### Reference
|
||||
{% for reference in story.references %}
|
||||
* {{ reference }}
|
||||
{% endfor %}
|
||||
|
||||
_version_: {{story.version}}
|
||||
</details>
|
||||
|
||||
---
|
||||
{% endfor %}
|
||||
</details>
|
||||
{% endfor %}
|
||||
@@ -0,0 +1,66 @@
|
||||
=Splunk Security Content Analytic Story =
|
||||
|
||||
----
|
||||
All the Analytic Stories shipped to different Splunk products. Below is a breakdown by Category.
|
||||
{% for category in categories %}
|
||||
=={{ category.name }}==
|
||||
|
||||
{% for story in category.stories %}
|
||||
==={{ story.name|capitalize }}===
|
||||
{{ story.description }}
|
||||
|
||||
* '''Product''': {{ story.tags.product|join(', ') }}
|
||||
* '''Datamodel''': {{ story.data_models|join(', ') }}
|
||||
* '''ATT&CK''': {% for attack in story.mitre_attacks %}[https://attack.mitre.org/techniques/{{ attack.technique_id }}/ {{ attack.technique_id }}]{% if not loop.last %}, {% endif %}{% endfor %}
|
||||
* '''Last Updated''': {{ story.date }}
|
||||
|
||||
<div class="toccolours mw-collapsible mw-collapsed">
|
||||
<div class="mw-collapsible-content">
|
||||
|
||||
====Detection Profile====
|
||||
{% for detection in story.detections %}
|
||||
* [[Documentation:ESSOC:detections:Detections#{{ detection|replace(" ", "_")|capitalize }}|{{ detection }}]]
|
||||
{% endfor %}
|
||||
|
||||
{% if story.mitre_attacks|length > 0 %}
|
||||
====ATT&CK====
|
||||
{|
|
||||
! style="text-align:left;"| ID
|
||||
! Technique
|
||||
! Tactic
|
||||
{%-for attack in story.mitre_attacks %}
|
||||
|-
|
||||
| {{ attack.technique_id }}
|
||||
| {{ attack.technique }}
|
||||
| {{ attack.tactic|join(', ') }}
|
||||
{%- endfor %}
|
||||
|}
|
||||
{% endif %}
|
||||
|
||||
====Kill Chain Phase====
|
||||
{% for phase in story.kill_chain_phases %}
|
||||
* {{ phase }}
|
||||
{% endfor %}
|
||||
|
||||
====Reference====
|
||||
{% for reference in story.references %}
|
||||
* {{ reference }}
|
||||
{% endfor %}
|
||||
|
||||
''version'': {{story.version}}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
----
|
||||
{% endfor %}
|
||||
|
||||
{% endfor %}
|
||||
|
||||
''#############''
|
||||
''# Automatically generated by doc_gen.py in https://github.com/splunk/security_content''
|
||||
''# On Date: {{ time }} UTC''
|
||||
''# Author: Splunk Security Research''
|
||||
''# Contact: research@splunk.com''
|
||||
''#############''
|
||||
|
||||
[[Category:V:ESSOC:drafts]]
|
||||
@@ -1,65 +0,0 @@
|
||||
= Use Case Categories=
|
||||
The collapse...
|
||||
|
||||
|
||||
{% for category in categories %}
|
||||
=={{ category.name }}==
|
||||
|
||||
{% for story in category.stories %}
|
||||
==={{ story.name }}===
|
||||
|
||||
{{ story.description }}
|
||||
|
||||
<div class="toccolours mw-collapsible">
|
||||
<div class="mw-collapsible-content">
|
||||
|
||||
====Narrative====
|
||||
{{ story.narrative }}
|
||||
|
||||
====Detections====
|
||||
{% for detection in story.detections %}
|
||||
* {{ detection }}
|
||||
{% endfor %}
|
||||
|
||||
====Data Models====
|
||||
{% for data_model in story.data_models %}
|
||||
* {{ data_model }}
|
||||
{% endfor %}
|
||||
|
||||
====Tags====
|
||||
|
||||
=====ATT&CK=====
|
||||
{% for mitre_attack_id in story.mitre_attack_ids %}
|
||||
* {{ mitre_attack_id }}
|
||||
{% endfor %}
|
||||
|
||||
=====Kill Chain Phases=====
|
||||
{% for kill_chain_phase in story.kill_chain_phases %}
|
||||
* {{ kill_chain_phase }}
|
||||
{% endfor %}
|
||||
|
||||
=====CIS=====
|
||||
{% for cis in story.ciss %}
|
||||
* {{ cis }}
|
||||
{% endfor %}
|
||||
|
||||
=====NIST=====
|
||||
{% for nist in story.nists %}
|
||||
* {{ nist }}
|
||||
{% endfor %}
|
||||
|
||||
====References====
|
||||
{% for reference in story.references %}
|
||||
* {{ reference }}
|
||||
{% endfor %}
|
||||
|
||||
date = {{ story.date }}
|
||||
|
||||
version = {{ story.version }}
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% endfor %}
|
||||
|
||||
{% endfor %}
|
||||
@@ -1,68 +0,0 @@
|
||||
|
||||
# Categories
|
||||
Analytics stories organized by categories
|
||||
{% for category in categories %}
|
||||
|
||||
* [{{ category.name }}](#{{ category.name | replace(' ','-') }})
|
||||
{% endfor %}
|
||||
|
||||
|
||||
{% for category in categories %}
|
||||
## {{ category.name }}
|
||||
{% for story in category.stories %}
|
||||
|
||||
* [{{ story.name }}](#{{ story.name | replace(' ','-') }})
|
||||
{% endfor %}
|
||||
|
||||
{% for story in category.stories %}
|
||||
### {{ story.name }}
|
||||
* id = {{ story.id }}
|
||||
* date = {{ story.date }}
|
||||
* version = {{ story.version }}
|
||||
|
||||
#### Description
|
||||
{{ story.description }}
|
||||
|
||||
#### Narrative
|
||||
{{ story.narrative }}
|
||||
|
||||
#### Detections
|
||||
{% for detection in story.detections %}
|
||||
* {{ detection }}
|
||||
{% endfor %}
|
||||
|
||||
#### Data Models
|
||||
{% for data_model in story.data_models %}
|
||||
* {{ data_model }}
|
||||
{% endfor %}
|
||||
|
||||
#### Mappings
|
||||
|
||||
##### ATT&CK
|
||||
{% for mitre_attack_id in story.mitre_attack_ids %}
|
||||
* {{ mitre_attack_id }}
|
||||
{% endfor %}
|
||||
|
||||
##### Kill Chain Phases
|
||||
{% for kill_chain_phase in story.kill_chain_phases %}
|
||||
* {{ kill_chain_phase }}
|
||||
{% endfor %}
|
||||
|
||||
###### CIS
|
||||
{% for cis in story.ciss %}
|
||||
* {{ cis }}
|
||||
{% endfor %}
|
||||
|
||||
##### NIST
|
||||
{% for nist in story.nists %}
|
||||
* {{ nist }}
|
||||
{% endfor %}
|
||||
|
||||
##### References
|
||||
{% for reference in story.references %}
|
||||
* {{ reference }}
|
||||
{% endfor %}
|
||||
|
||||
{% endfor %}
|
||||
|
||||
{% endfor %}
|
||||
@@ -2,8 +2,6 @@
|
||||
import git
|
||||
import os
|
||||
import logging
|
||||
from os import path
|
||||
import sys
|
||||
|
||||
|
||||
# Logger
|
||||
@@ -25,7 +23,6 @@ class GithubService:
|
||||
repo_obj = git.Repo.clone_from(url, project, branch=branch)
|
||||
return repo_obj
|
||||
|
||||
|
||||
def get_changed_test_files_ssa(self):
|
||||
branch1 = self.security_content_branch
|
||||
branch2 = 'develop'
|
||||
@@ -35,8 +32,6 @@ class GithubService:
|
||||
|
||||
changed_ssa_test_files = []
|
||||
|
||||
#tests = self.read_security_content_test_files()
|
||||
|
||||
for file_path in changed_files:
|
||||
# added or changed test files
|
||||
if file_path.startswith('tests'):
|
||||
@@ -47,7 +42,10 @@ class GithubService:
|
||||
# changed detections
|
||||
if file_path.startswith('detections'):
|
||||
if os.path.basename(file_path).startswith('ssa'):
|
||||
file_path_new = os.path.splitext(file_path)[0].replace('detections', 'tests') + '.test.yml'
|
||||
file_path_base = os.path.splitext(file_path)[0].replace('detections', 'tests') + '.test'
|
||||
file_path_new = file_path_base + '.yml'
|
||||
if not os.path.exists(file_path_new):
|
||||
file_path_new = file_path_base + '.yaml'
|
||||
if file_path_new not in changed_ssa_test_files:
|
||||
changed_ssa_test_files.append(file_path_new)
|
||||
|
||||
|
||||
@@ -17,4 +17,5 @@
|
||||
| eval start_time = timestamp,
|
||||
end_time = timestamp,
|
||||
entities = mvappend(dest_device_id, dest_user_id),
|
||||
body = "TBD";
|
||||
body = "TBD"
|
||||
| into write_ssa_detected_events();
|
||||
@@ -17,4 +17,5 @@
|
||||
| eval start_time = timestamp,
|
||||
end_time = timestamp,
|
||||
entities = mvappend(dest_device_id, dest_user_id),
|
||||
body = "TBD";
|
||||
body = "TBD"
|
||||
| into write_ssa_detected_events();
|
||||
|
||||
@@ -1 +1 @@
|
||||
| from read_splunk_firehose();
|
||||
| from read_splunk_firehose();
|
||||
@@ -1 +1 @@
|
||||
| from read_ssa_enriched_events();
|
||||
| from read_ssa_enriched_events() | into write_ssa_detected_events();
|
||||
@@ -1,4 +1,3 @@
|
||||
|
||||
import logging
|
||||
import os
|
||||
import time
|
||||
@@ -6,8 +5,7 @@ import sys
|
||||
|
||||
from http import HTTPStatus
|
||||
from modules.streams_service_api_helper import DSPApi
|
||||
from modules.utils import manipulate_spl, read_spl, read_data
|
||||
|
||||
from modules.utils import check_source_sink, manipulate_spl, read_spl, read_data
|
||||
|
||||
# Logger
|
||||
logging.basicConfig(level=os.environ.get("LOGLEVEL", "INFO"))
|
||||
@@ -22,6 +20,7 @@ MAX_EXECUTION_TIME_LIMIT = 600 # per detection test
|
||||
|
||||
TEST_DATASET = 'windows-security_small.txt'
|
||||
|
||||
|
||||
class SSADetectionTesting:
|
||||
|
||||
def __init__(self, env, tenant, header_token):
|
||||
@@ -45,7 +44,7 @@ class SSADetectionTesting:
|
||||
]
|
||||
|
||||
test_results = []
|
||||
for i in range(0,len(test_spls)):
|
||||
for i in range(0, len(test_spls)):
|
||||
self.max_execution_time = MAX_EXECUTION_TIME_LIMIT
|
||||
test_result = self.ssa_detection_test(read_spl(file_path_spl, test_spls[i]), file_path_data, test_names[i])
|
||||
test_results.append(test_result.copy())
|
||||
@@ -62,17 +61,16 @@ class SSADetectionTesting:
|
||||
|
||||
return passed
|
||||
|
||||
|
||||
def test_ssa_detections(self, test_obj):
|
||||
LOGGER.info('Test SSA Detection: ' + test_obj["detection_obj"]["name"])
|
||||
self.max_execution_time = MAX_EXECUTION_TIME_LIMIT
|
||||
file_path_attack_data = os.path.join(os.path.dirname(__file__), "../", test_obj["attack_data_file_path"])
|
||||
|
||||
test_results = self.ssa_detection_test(test_obj["detection_obj"]["search"], file_path_attack_data, "SSA Smoke Test " + test_obj["test_obj"]["name"])
|
||||
test_results = self.ssa_detection_test(test_obj["detection_obj"]["search"], file_path_attack_data,
|
||||
"SSA Smoke Test " + test_obj["test_obj"]["name"])
|
||||
|
||||
return test_results
|
||||
|
||||
|
||||
## Helper Functions ##
|
||||
|
||||
def update_execution_time(self, time_frame):
|
||||
@@ -86,58 +84,45 @@ class SSADetectionTesting:
|
||||
time.sleep(time_in_s)
|
||||
return self.update_execution_time(time_in_s)
|
||||
|
||||
def check_result(self, condition, error_message):
|
||||
try:
|
||||
assert condition
|
||||
except:
|
||||
self.execution_passed = False
|
||||
LOGGER.error(error_message)
|
||||
|
||||
def write_test_results(self, test_name):
|
||||
if not self.execution_passed:
|
||||
msg = f"Detection test failed for {test_name}"
|
||||
LOGGER.error(msg)
|
||||
self.test_results["msg"] = msg
|
||||
self.test_results["result"] = False
|
||||
else:
|
||||
msg = f"Detection test successful for {test_name}"
|
||||
LOGGER.info(msg)
|
||||
self.test_results["msg"] = msg
|
||||
|
||||
|
||||
def ssa_detection_test_init(self):
|
||||
self.test_results["result"] = True
|
||||
self.test_results["msg"] = ""
|
||||
self.results_index = self.api.create_temp_index("mc")
|
||||
|
||||
self.created_pipelines = []
|
||||
self.activated_pipelines = []
|
||||
|
||||
def ssa_detection_test_main(self, spl, source, test_name):
|
||||
self.execution_passed = True
|
||||
|
||||
self.wait_time(SLEEP_TIME_CREATE_INDEX)
|
||||
|
||||
check_ssa_spl = check_source_sink(spl)
|
||||
spl = manipulate_spl(self.api.env, spl, self.results_index)
|
||||
self.check_result(spl is not None, "fail to manipulate spl file")
|
||||
assert spl is not None, "fail to manipulate spl file"
|
||||
|
||||
pipeline_id = self.api.create_pipeline_from_spl(spl)
|
||||
self.check_result(pipeline_id is not None, "failed to create a pipeline")
|
||||
assert pipeline_id is not None, "failed to create a pipeline"
|
||||
|
||||
_pipeline_status = self.api.pipeline_status(pipeline_id)
|
||||
self.check_result(_pipeline_status=="CREATED", f"Current status of pipeline {pipeline_id} should be CREATED")
|
||||
assert _pipeline_status == "CREATED", f"Current status of pipeline {pipeline_id} should be CREATED"
|
||||
self.created_pipelines.append(pipeline_id)
|
||||
|
||||
response_body = self.api.activate_pipeline(pipeline_id)
|
||||
self.check_result(response_body.get("activated")==pipeline_id, f"pipeline {pipeline_id} should be successfully activate.")
|
||||
assert response_body.get("activated") == pipeline_id, f"pipeline {pipeline_id} should be successfully activate."
|
||||
self.activated_pipelines.append(pipeline_id)
|
||||
|
||||
self.wait_time(SLEEP_TIME_ACTIVATE_PIPELINE)
|
||||
|
||||
if not check_ssa_spl:
|
||||
msg = f"Detection test successful for {test_name}"
|
||||
LOGGER.warning(f"Test not completed. Detection seems deprecated, and will not send messages to SSA")
|
||||
self.test_results["msg"] = msg
|
||||
return self.test_results
|
||||
|
||||
data = read_data(source)
|
||||
LOGGER.info("Sending (%d) events" % (len(data)))
|
||||
|
||||
if len(data) == 0:
|
||||
LOGGER.warning("No events to send, skip to next test.")
|
||||
self.execution_passed = False
|
||||
self.write_test_results(test_name)
|
||||
return self.test_results
|
||||
assert len(data) > 0, "No events to send, skip to next test."
|
||||
|
||||
for d in data:
|
||||
response_body = self.api.ingest_data(d)
|
||||
@@ -151,8 +136,8 @@ class SSADetectionTesting:
|
||||
max_execution_time_reached = self.wait_time(WAIT_CYCLE)
|
||||
query = f"from indexes('{self.results_index['name']}') | search source!=\"Search Catalog\" "
|
||||
sid = self.api.submit_search_job(self.results_index['module'], query)
|
||||
self.check_result(sid is not None, f"Failed to create a Search Job")
|
||||
|
||||
assert sid is not None, f"Failed to create a Search Job"
|
||||
|
||||
job_finished = False
|
||||
while not job_finished:
|
||||
self.wait_time(WAIT_CYCLE)
|
||||
@@ -162,33 +147,53 @@ class SSADetectionTesting:
|
||||
results = self.api.get_search_job_results(sid)
|
||||
search_results = (len(results) > 0)
|
||||
if not search_results:
|
||||
LOGGER.info(f"Search didn't return any results. Retrying in {WAIT_CYCLE}s, max execution time left {self.max_execution_time}s")
|
||||
|
||||
self.check_result(len(results) > 0, "Search job didn't return any results")
|
||||
LOGGER.info(
|
||||
f"Search didn't return any results. Retrying in {WAIT_CYCLE}s, max execution time left {self.max_execution_time}s")
|
||||
|
||||
response, response_body = self.api.deactivate_pipeline(pipeline_id)
|
||||
self.check_result(response.status_code == HTTPStatus.OK, f"The pipeline {pipeline_id} fails to deactivated.")
|
||||
assert len(results) > 0, "Search job didn't return any results"
|
||||
|
||||
response = self.api.delete_pipeline(pipeline_id)
|
||||
self.check_result(response.status_code == HTTPStatus.NO_CONTENT, f"Fail to delete pipeline {pipeline_id}.")
|
||||
|
||||
self.write_test_results(test_name)
|
||||
msg = f"Detection test successful for {test_name}"
|
||||
LOGGER.info(msg)
|
||||
self.test_results["msg"] = msg
|
||||
|
||||
return self.test_results
|
||||
|
||||
|
||||
def ssa_detection_test_teardown(self):
|
||||
pass
|
||||
self.api.delete_temp_index(self.results_index["id"])
|
||||
|
||||
"""
|
||||
Deactivate and deletes pipelines, deletes results indexes,
|
||||
and when it fails it shows pipelines and result indexes that were not removed.
|
||||
:return:
|
||||
None
|
||||
"""
|
||||
deactivate_pipeline = lambda p: self.api.deactivate_pipeline(p)[0].status_code == HTTPStatus.OK
|
||||
delete_pipeline = lambda p: self.api.delete_pipeline(p).status_code == HTTPStatus.NO_CONTENT
|
||||
delete_index = lambda p: self.api.delete_temp_index(p["id"]) == HTTPStatus.NO_CONTENT
|
||||
self.activated_pipelines = [p for p in self.activated_pipelines if not deactivate_pipeline(p)]
|
||||
self.created_pipelines = [p for p in self.created_pipelines if not delete_pipeline(p)]
|
||||
if len(self.activated_pipelines) > 0 or len(self.created_pipelines) > 0 or not delete_index(self.results_index):
|
||||
LOGGER.warning("Not all SCS resources fred up")
|
||||
LOGGER.info(f"Created Pipelines: {','.join(self.created_pipelines)}")
|
||||
LOGGER.info(f"Active Pipelines: {','.join(self.activated_pipelines)}")
|
||||
LOGGER.info(f"Result Indexes: {self.results_index}")
|
||||
else:
|
||||
LOGGER.info("Testing successfully cleaned up")
|
||||
|
||||
def ssa_detection_test(self, spl, source, test_name):
|
||||
self.ssa_detection_test_init()
|
||||
test_result = self.ssa_detection_test_main(spl, source, test_name)
|
||||
self.ssa_detection_test_teardown()
|
||||
return test_result
|
||||
|
||||
|
||||
try:
|
||||
test_result = self.ssa_detection_test_main(spl, source, test_name)
|
||||
self.ssa_detection_test_teardown()
|
||||
return test_result
|
||||
except AssertionError as e:
|
||||
self.ssa_detection_test_teardown()
|
||||
LOGGER.error(e.args[0])
|
||||
return {"result": False,
|
||||
"msg": f"Detection test failure for {test_name}"}
|
||||
except Exception as e:
|
||||
self.ssa_detection_test_teardown()
|
||||
LOGGER.error(e)
|
||||
return {"result": False,
|
||||
"msg": f"Detection test failure for {test_name} (perhaps SCS problems)"}
|
||||
|
||||
# only for troubleshooting
|
||||
# def ssa_detection_in_dsp_with_preview_session(self, spl, source, test_name):
|
||||
@@ -213,4 +218,4 @@ class SSADetectionTesting:
|
||||
|
||||
# response = self.api.stop_preview_session(preview_id)
|
||||
|
||||
# self.write_test_results(test_name)
|
||||
# self.write_test_results(test_name)
|
||||
|
||||
@@ -75,14 +75,26 @@ def request_headers(header_token):
|
||||
return headers
|
||||
|
||||
|
||||
def check_source_sink(spl):
|
||||
match_source = re.match(r"^\s*\|\s+from\s+read_ssa_enriched_events\(\s*\)", spl)
|
||||
match_sink = re.search(r"\|\s*into\s+write_ssa_detected_events\(\s*\)\s*;", spl)
|
||||
return match_source and match_sink
|
||||
|
||||
|
||||
def manipulate_spl(env, spl, results_index):
|
||||
spl = replace_ssa_macros(env, spl)
|
||||
# Obtain the SSA source
|
||||
pulsar_source_connection_id, pulsar_source_topic = return_macros(env)
|
||||
source = READ_SSA_ENRICHED_EVENTS_EXPANDED\
|
||||
.replace("__PULSAR_SOURCE_CONNECTION_ID__", pulsar_source_connection_id)\
|
||||
.replace("__PULSAR_SOURCE_TOPIC__", pulsar_source_topic)
|
||||
# Obtain the test sink
|
||||
sink = ";"
|
||||
if results_index is not None:
|
||||
# When an index is defined for a test, it writes the output of this pipeline to this index.
|
||||
# original_pipeline; => original_pipeline | into index("module", "index");
|
||||
module = results_index["module"]
|
||||
index = results_index["name"]
|
||||
spl = spl[:spl.rindex(";")] + f" | into index(\"{module}\", \"{index}\");"
|
||||
sink = f"| into index(\"{module}\", \"{index}\");"
|
||||
# Replace spl template with its `source` and `sink`
|
||||
spl = replace_ssa_macros(source, sink, spl)
|
||||
LOGGER.info(f"spl: {spl}")
|
||||
return spl
|
||||
|
||||
@@ -93,13 +105,9 @@ def read_spl(file_path, file_name):
|
||||
return spl
|
||||
|
||||
|
||||
def replace_ssa_macros(env, spl):
|
||||
pulsar_source_connection_id, pulsar_source_topic = return_macros(env)
|
||||
macro_expanded = READ_SSA_ENRICHED_EVENTS_EXPANDED.replace("__PULSAR_SOURCE_CONNECTION_ID__", pulsar_source_connection_id)
|
||||
macro_expanded = macro_expanded.replace("__PULSAR_SOURCE_TOPIC__", pulsar_source_topic)
|
||||
spl = spl.replace(READ_SSA_ENRICHED_EVENTS, macro_expanded)
|
||||
spl = spl.replace(WRITE_SSA_DETECTED_EVENTS, ";")
|
||||
#spl = spl.replace("\n", " ")
|
||||
def replace_ssa_macros(source, sink, spl):
|
||||
spl = spl.replace(READ_SSA_ENRICHED_EVENTS, source)
|
||||
spl = spl.replace(WRITE_SSA_DETECTED_EVENTS, sink)
|
||||
return spl
|
||||
|
||||
|
||||
|
||||
@@ -38,7 +38,7 @@ def main(args):
|
||||
for test_file in test_files_ssa:
|
||||
LOGGER.info(test_file)
|
||||
|
||||
if len(test_files_ssa)==0:
|
||||
if len(test_files_ssa) == 0:
|
||||
LOGGER.info('Nothing to test for SSA smoke test.')
|
||||
sys.exit(0)
|
||||
|
||||
|
||||
@@ -0,0 +1,55 @@
|
||||
name: Clop Common Exec Parameter
|
||||
id: 5a8a2a72-8322-11eb-9ee9-acde48001122
|
||||
version: 1
|
||||
date: '2021-03-17'
|
||||
author: Teoderick Contreras, Splunk
|
||||
type: batch
|
||||
datamodel:
|
||||
- Endpoint
|
||||
description: The following analytics are designed to identifies some CLOP ransomware
|
||||
variant that using arguments to execute its main code or feature of its code. In
|
||||
this variant if the parameter is "runrun", CLOP ransomware will try to encrypt files
|
||||
in network shares and if it is "temp.dat", it will try to read from some stream
|
||||
pipe or file start encrypting files within the infected local machines. This technique
|
||||
can be also identified as an anti-sandbox technique to make its code non-responsive
|
||||
since it is waiting for some parameter to execute properly.
|
||||
search: '| tstats `security_content_summariesonly` values(Processes.process) as cmdline
|
||||
values(Processes.parent_process_name) as parent_process values(Processes.process_name)
|
||||
count min(_time) as firstTime max(_time) as lastTime from datamodel=Endpoint.Processes
|
||||
where Processes.process = "*runrun*" OR Processes.process = "*temp.dat*" by Processes.parent_process_name
|
||||
Processes.process_name Processes.process Processes.dest Processes.user Processes.process_id Processes.process_guid
|
||||
| `drop_dm_object_name(Processes)`
|
||||
| `security_content_ctime(firstTime)`
|
||||
| `security_content_ctime(lastTime)`
|
||||
| `clop_common_exec_parameter_filter`'
|
||||
how_to_implement: To successfully implement this search, you need to be ingesting
|
||||
logs with the process name, parent process, and command-line executions from your
|
||||
endpoints. If you are using Sysmon, you must have at least version 6.0.4 of the
|
||||
Sysmon TA.
|
||||
known_false_positives: Operators can execute third party tools using these parameters.
|
||||
references:
|
||||
- https://www.fireeye.com/blog/threat-research/2020/10/fin11-email-campaigns-precursor-for-ransomware-data-theft.html
|
||||
- https://blog.virustotal.com/2020/11/keep-your-friends-close-keep-ransomware.html
|
||||
tags:
|
||||
analytic_story:
|
||||
- Clop Ransomware
|
||||
automated_detection_testing: passed
|
||||
kill_chain_phases:
|
||||
- Obfuscation
|
||||
mitre_attack_id:
|
||||
- T1204
|
||||
product:
|
||||
- Splunk Enterprise
|
||||
- Splunk Enterprise Security
|
||||
- Splunk Cloud
|
||||
required_fields:
|
||||
- Processes.process
|
||||
- Processes.parent_process_name
|
||||
- _time
|
||||
- Processes.process_name
|
||||
- Processes.dest
|
||||
- Processes.user
|
||||
- Processes.process_id
|
||||
security_domain: endpoint
|
||||
dataset:
|
||||
- https://media.githubusercontent.com/media/splunk/attack_data/master/datasets/malware/clop/clop_b/windows-sysmon.log
|
||||
@@ -0,0 +1,46 @@
|
||||
name: Clop Ransomware Known Service Name
|
||||
id: 07e08a12-870c-11eb-b5f9-acde48001122
|
||||
version: 1
|
||||
date: '2021-03-17'
|
||||
author: Teoderick Contreras
|
||||
type: batch
|
||||
datamodel:
|
||||
- Endpoint
|
||||
description: This detection is to identify the common service name created by the
|
||||
CLOP ransomware as part of its persistence and high privilege code execution in
|
||||
the infected machine. Ussually CLOP ransomware use StartServiceCtrlDispatcherW API
|
||||
in creating this service entry.
|
||||
search: '`wineventlog_system` EventCode=7045 Service_Name IN ("SecurityCenterIBM",
|
||||
"WinCheckDRVs") | stats count min(_time) as firstTime max(_time) as lastTime by
|
||||
EventCode Service_File_Name Service_Name Service_Start_Type Service_Type | `security_content_ctime(firstTime)`
|
||||
| `security_content_ctime(lastTime)` | `clop_ransomware_known_service_name_filter`'
|
||||
how_to_implement: To successfully implement this search, you need to be ingesting
|
||||
logs with the Service name, Service File Name Service Start type, and Service Type
|
||||
from your endpoints.
|
||||
known_false_positives: unknown
|
||||
references:
|
||||
- https://www.fireeye.com/blog/threat-research/2020/10/fin11-email-campaigns-precursor-for-ransomware-data-theft.html
|
||||
- https://blog.virustotal.com/2020/11/keep-your-friends-close-keep-ransomware.html
|
||||
tags:
|
||||
analytic_story:
|
||||
- Clop Ransomware
|
||||
kill_chain_phases:
|
||||
- Privilege Escalation
|
||||
mitre_attack_id:
|
||||
- T1543
|
||||
product:
|
||||
- Splunk Enterprise
|
||||
- Splunk Enterprise Security
|
||||
- Splunk Cloud
|
||||
required_fields:
|
||||
- EventCode
|
||||
- cmdline
|
||||
- _time
|
||||
- parent_process_name
|
||||
- process_name
|
||||
- OriginalFileName
|
||||
- process_path
|
||||
security_domain: endpoint
|
||||
automated_detection_testing: passed
|
||||
dataset:
|
||||
- https://media.githubusercontent.com/media/splunk/attack_data/master/datasets/malware/clop/clop_a/windows-system.log
|
||||
@@ -40,6 +40,7 @@ tags:
|
||||
- SamSam Ransomware
|
||||
- Ryuk Ransomware
|
||||
- Ransomware
|
||||
- Clop Ransomware
|
||||
asset_type: Endpoint
|
||||
automated_detection_testing: passed
|
||||
cis20:
|
||||
|
||||
@@ -26,6 +26,7 @@ tags:
|
||||
- SamSam Ransomware
|
||||
- Ransomware
|
||||
- Ryuk Ransomware
|
||||
- Clop Ransomware
|
||||
asset_type: Endpoint
|
||||
automated_detection_testing: passed
|
||||
cis20:
|
||||
|
||||
@@ -0,0 +1,44 @@
|
||||
name: Create Service In Suspicious File Path
|
||||
id: 429141be-8311-11eb-adb6-acde48001122
|
||||
version: 1
|
||||
date: '2021-03-12'
|
||||
author: Teoderick Contreras
|
||||
type: batch
|
||||
datamodel:
|
||||
- Endpoint
|
||||
description: This detection is to identify a creation of "user mode service" where
|
||||
the service file path is located in non-common service folder in windows.
|
||||
search: ' `wineventlog_system` EventCode=7045 Service_File_Name = "*\.exe" NOT (Service_File_Name
|
||||
IN ("C:\\Windows\\*", "C:\\Program File*", "C:\\Programdata\\*", "%systemroot%\\*"))
|
||||
Service_Type = "user mode service" | stats count min(_time) as firstTime max(_time)
|
||||
as lastTime by EventCode Service_File_Name Service_Name Service_Start_Type Service_Type
|
||||
| `security_content_ctime(firstTime)` | `security_content_ctime(lastTime)` | `create_service_in_suspicious_file_path_filter`'
|
||||
how_to_implement: To successfully implement this search, you need to be ingesting
|
||||
logs with the Service name, Service File Name Service Start type, and Service Type
|
||||
from your endpoints.
|
||||
known_false_positives: unknown
|
||||
references:
|
||||
- https://www.fireeye.com/blog/threat-research/2020/10/fin11-email-campaigns-precursor-for-ransomware-data-theft.html
|
||||
- https://blog.virustotal.com/2020/11/keep-your-friends-close-keep-ransomware.html
|
||||
tags:
|
||||
analytic_story:
|
||||
- Clop Ransomware
|
||||
kill_chain_phases:
|
||||
- Privilege Escalation
|
||||
mitre_attack_id:
|
||||
- T1569.001, T1569.002
|
||||
product:
|
||||
- Splunk Enterprise
|
||||
- Splunk Enterprise Security
|
||||
- Splunk Cloud
|
||||
required_fields:
|
||||
- EventCode
|
||||
- Service_File_Name
|
||||
- Service_Type
|
||||
- _time
|
||||
- Service_Name
|
||||
- Service_Start_Type
|
||||
security_domain: endpoint
|
||||
automated_detection_testing: passed
|
||||
dataset:
|
||||
- https://media.githubusercontent.com/media/splunk/attack_data/master/datasets/malware/clop/clop_a/windows-system.log
|
||||
@@ -29,6 +29,7 @@ tags:
|
||||
- Windows Log Manipulation
|
||||
- SamSam Ransomware
|
||||
- Ransomware
|
||||
- Clop Ransomware
|
||||
asset_type: Endpoint
|
||||
automated_detection_testing: passed
|
||||
cis20:
|
||||
|
||||
@@ -0,0 +1,48 @@
|
||||
name: High File Deletion Frequency
|
||||
id: 45b125c4-866f-11eb-a95a-acde48001122
|
||||
version: 1
|
||||
date: '2021-03-16'
|
||||
author: Teoderick Contreras
|
||||
type: batch
|
||||
datamodel:
|
||||
- Endpoint
|
||||
description: This search looks for high frequency of file deletion relative to process
|
||||
name and process id. These events usually happen when the ransomware tries to encrypt
|
||||
the files with the ransomware file extensions and sysmon treat the original files
|
||||
to be deleted as soon it was replace as encrypted data.
|
||||
search: '`sysmon` EventCode=23 TargetFilename IN ("*\.cmd", "*\.ini","*\.gif", "*\.jpg",
|
||||
"*\.jpeg", "*\.db", "*\.ps1", "*\.doc*", "*\.xls*", "*\.ppt*", "*\.bmp","*\.zip",
|
||||
"*\.rar", "*\.7z", "*\.chm", "*\.png", "*\.log", "*\.vbs", "*\.js") | stats values(TargetFilename)
|
||||
as deleted_files min(_time) as firstTime max(_time) as lastTime count by Computer
|
||||
user EventCode Image ProcessID |where count >=100 | `security_content_ctime(firstTime)`
|
||||
| `security_content_ctime(lastTime)` | `high_file_deletion_frequency_filter`'
|
||||
how_to_implement: To successfully implement this search, you need to be ingesting
|
||||
logs with the deleted target file name, process name and process id from your endpoints.
|
||||
If you are using Sysmon, you must have at least version 6.0.4 of the Sysmon TA.
|
||||
known_false_positives: user may delete bunch of pictures or files in a folder.
|
||||
references:
|
||||
- https://www.fireeye.com/blog/threat-research/2020/10/fin11-email-campaigns-precursor-for-ransomware-data-theft.html
|
||||
- https://blog.virustotal.com/2020/11/keep-your-friends-close-keep-ransomware.html
|
||||
tags:
|
||||
analytic_story:
|
||||
- Clop Ransomware
|
||||
kill_chain_phases:
|
||||
- Exploitation
|
||||
mitre_attack_id:
|
||||
- T1485
|
||||
product:
|
||||
- Splunk Enterprise
|
||||
- Splunk Enterprise Security
|
||||
- Splunk Cloud
|
||||
required_fields:
|
||||
- EventCode
|
||||
- TargetFilename
|
||||
- Computer
|
||||
- user
|
||||
- Image
|
||||
- ProcessID
|
||||
- _time
|
||||
security_domain: endpoint
|
||||
automated_detection_testing: passed
|
||||
dataset:
|
||||
- https://media.githubusercontent.com/media/splunk/attack_data/master/datasets/malware/clop/clop_a/windows-sysmon.log
|
||||
@@ -0,0 +1,44 @@
|
||||
name: High Process Termination Frequency
|
||||
id: 17cd75b2-8666-11eb-9ab4-acde48001122
|
||||
version: 1
|
||||
date: '2021-03-16'
|
||||
author: Teoderick Contreras
|
||||
type: batch
|
||||
datamodel:
|
||||
- Endpoint
|
||||
description: This analytics are designed to indentify a high frequency of process
|
||||
termination on a machine which is a common behavior of ransomware malware before
|
||||
encrypting files. This technique is designed to avoid an exception error while accessing
|
||||
(docs, images, database and etc..) in the infected machine for encryption.
|
||||
search: '`sysmon` EventCode=5 |bin _time span=3s |stats values(Image) as proc_terminated
|
||||
min(_time) as firstTime max(_time) as lastTime count by Computer EventCode ProcessID
|
||||
| where count >= 15 | `security_content_ctime(firstTime)`| `security_content_ctime(lastTime)`
|
||||
| `high_process_termination_frequency_filter`'
|
||||
how_to_implement: To successfully implement this search, you need to be ingesting
|
||||
logs with the Image (process full path of terminated process) from your endpoints.
|
||||
If you are using Sysmon, you must have at least version 6.0.4 of the Sysmon TA.
|
||||
known_false_positives: admin or user tool that can terminate multiple process.
|
||||
references:
|
||||
- https://www.fireeye.com/blog/threat-research/2020/10/fin11-email-campaigns-precursor-for-ransomware-data-theft.html
|
||||
- https://blog.virustotal.com/2020/11/keep-your-friends-close-keep-ransomware.html
|
||||
tags:
|
||||
analytic_story:
|
||||
- Clop Ransomware
|
||||
kill_chain_phases:
|
||||
- Exploitation
|
||||
mitre_attack_id:
|
||||
- T1486
|
||||
product:
|
||||
- Splunk Enterprise
|
||||
- Splunk Enterprise Security
|
||||
- Splunk Cloud
|
||||
required_fields:
|
||||
- EventCode
|
||||
- Image
|
||||
- Computer
|
||||
- _time
|
||||
- ProcessID
|
||||
security_domain: endpoint
|
||||
automated_detection_testing: passed
|
||||
dataset:
|
||||
- https://media.githubusercontent.com/media/splunk/attack_data/master/datasets/malware/clop/clop_a/windows-sysmon.log
|
||||
@@ -0,0 +1,53 @@
|
||||
name: Process Deleting Its Process File Path
|
||||
id: f7eda4bc-871c-11eb-b110-acde48001122
|
||||
version: 1
|
||||
date: '2021-03-17'
|
||||
author: Teoderick Contreras
|
||||
type: batch
|
||||
datamodel:
|
||||
- Endpoint
|
||||
description: This detection is to identify a suspicious process that tries to delete
|
||||
the process file path related to its process. This technique is known to be defense
|
||||
evasion once a certain condition of malware is satisfied or not. Clop ransomware
|
||||
use this technique where it will try to delete its process file path using a .bat
|
||||
command if the keyboard layout is not the layout it tries to infect.
|
||||
search: '`sysmon` EventCode=1 cmdline = "*/c del*" Image = "*\\cmd.exe" |eval result
|
||||
= if(like(process,"%".parent_process."%"), "Found", "Not Found") | stats min(_time)
|
||||
as firstTime max(_time) as lastTime count by Computer user ParentImage ParentCommandLine
|
||||
Image cmdline EventCode ProcessID result | where result = "Found" | `security_content_ctime(firstTime)`
|
||||
| `security_content_ctime(lastTime)` | `process_deleting_its_process_file_path_filter`'
|
||||
how_to_implement: You must be ingesting data that records process activity from your
|
||||
hosts to populate the Endpoint data model in the Processes node. You must also be
|
||||
ingesting logs with both the process name and command line from your endpoints.
|
||||
The command-line arguments are mapped to the "process" field in the Endpoint data
|
||||
model.
|
||||
known_false_positives: unknown
|
||||
references:
|
||||
- https://www.fireeye.com/blog/threat-research/2020/10/fin11-email-campaigns-precursor-for-ransomware-data-theft.html
|
||||
- https://blog.virustotal.com/2020/11/keep-your-friends-close-keep-ransomware.html
|
||||
tags:
|
||||
analytic_story:
|
||||
- Clop Ransomware
|
||||
kill_chain_phases:
|
||||
- Exploitation
|
||||
mitre_attack_id:
|
||||
- T1003.002
|
||||
product:
|
||||
- Splunk Enterprise
|
||||
- Splunk Enterprise Security
|
||||
- Splunk Cloud
|
||||
required_fields:
|
||||
- EventCode
|
||||
- Computer
|
||||
- user
|
||||
- ParentImage
|
||||
- ParentCommandLine
|
||||
- Image
|
||||
- cmdline
|
||||
- ProcessID
|
||||
- result
|
||||
- _time
|
||||
security_domain: endpoint
|
||||
automated_detection_testing: passed
|
||||
dataset:
|
||||
- https://media.githubusercontent.com/media/splunk/attack_data/master/datasets/malware/clop/clop_a/windows-sysmon.log
|
||||
@@ -0,0 +1,48 @@
|
||||
name: Ransomware Notes bulk creation
|
||||
id: eff7919a-8330-11eb-83f8-acde48001122
|
||||
version: 1
|
||||
date: '2021-03-12'
|
||||
author: Teoderick Contreras
|
||||
type: batch
|
||||
datamodel:
|
||||
- Endpoint
|
||||
description: The following analytics identifies a big number of instance of ransomware
|
||||
notes (filetype e.g .txt, .html, .hta) file creation to the infected machine. This
|
||||
behavior is a good sensor if the ransomware note filename is quite new for security
|
||||
industry or the ransomware note filename is not in your lookup table list for monitoring.
|
||||
search: '`sysmon` EventCode=11 file_name IN ("*\.txt","*\.html","*\.hta") | stats
|
||||
min(_time) as firstTime max(_time) as lastTime dc(TargetFilename) as unique_readme_path_count
|
||||
values(TargetFilename) as list_of_readme_path by Computer Image file_name | where
|
||||
unique_readme_path_count >= 50 | `security_content_ctime(firstTime)` | `security_content_ctime(lastTime)`
|
||||
| `ransomware_notes_bulk_creation_filter`'
|
||||
how_to_implement: You must be ingesting data that records the filesystem activity
|
||||
from your hosts to populate the Endpoint file-system data model node. If you are
|
||||
using Sysmon, you will need a Splunk Universal Forwarder on each endpoint from which
|
||||
you want to collect data.
|
||||
known_false_positives: unknown
|
||||
references:
|
||||
- https://www.fireeye.com/blog/threat-research/2020/10/fin11-email-campaigns-precursor-for-ransomware-data-theft.html
|
||||
- https://blog.virustotal.com/2020/11/keep-your-friends-close-keep-ransomware.html
|
||||
tags:
|
||||
analytic_story:
|
||||
- Clop Ransomware
|
||||
kill_chain_phases:
|
||||
- Obfuscation
|
||||
mitre_attack_id:
|
||||
- T1486
|
||||
product:
|
||||
- Splunk Enterprise
|
||||
- Splunk Enterprise Security
|
||||
- Splunk Cloud
|
||||
required_fields:
|
||||
- EventCode
|
||||
- file_name
|
||||
- _time
|
||||
- TargetFilename
|
||||
- Computer
|
||||
- Image
|
||||
- user
|
||||
security_domain: endpoint
|
||||
automated_detection_testing: passed
|
||||
dataset:
|
||||
- https://media.githubusercontent.com/media/splunk/attack_data/master/datasets/malware/clop/clop_a/windows-sysmon.log
|
||||
@@ -0,0 +1,58 @@
|
||||
name: Resize ShadowStorage volume
|
||||
id: bc760ca6-8336-11eb-bcbb-acde48001122
|
||||
version: 1
|
||||
date: '2021-03-12'
|
||||
author: Teoderick Contreras
|
||||
type: batch
|
||||
datamodel:
|
||||
- Endpoint
|
||||
description: The following analytics identifies the resizing of shadowstorage by ransomware
|
||||
malware to avoid the shadow volumes being made again. this technique is an alternative
|
||||
by ransomware attacker than deleting the shadowstorage which is known alert in defensive
|
||||
team. one example of ransomware that use this technique is CLOP ransomware where
|
||||
it drops a .bat file that will resize the shadowstorage to minimum size as much
|
||||
as possible
|
||||
search: '| tstats `security_content_summariesonly` values(Processes.process) as cmdline
|
||||
values(Processes.parent_process_name) as parent_process values(Processes.process_name)
|
||||
as process_name min(_time) as firstTime max(_time) as lastTime from datamodel=Endpoint.Processes
|
||||
where Processes.parent_process_name = "cmd.exe" OR Processes.parent_process_name
|
||||
= "powershell.exe" OR Processes.parent_process_name = "powershell_ise.exe" OR Processes.parent_process_name
|
||||
= "wmic.exe" Processes.process_name = "vssadmin.exe" Processes.process="*resize*"
|
||||
Processes.process="*shadowstorage*" Processes.process="*/maxsize*" by Processes.parent_process_name
|
||||
Processes.parent_process Processes.process_name Processes.process Processes.dest
|
||||
Processes.user Processes.process_id Processes.process_guid
|
||||
| `drop_dm_object_name(Processes)`
|
||||
| `security_content_ctime(firstTime)`
|
||||
|`security_content_ctime(lastTime)`
|
||||
| `resize_shadowstorage_volume_filter`'
|
||||
how_to_implement: To successfully implement this search, you need to be ingesting
|
||||
logs with the process name, parent process, and command-line executions from your
|
||||
endpoints. If you are using Sysmon, you must have at least version 6.0.4 of the
|
||||
Sysmon TA.
|
||||
known_false_positives: network admin can resize the shadowstorage for valid purposes.
|
||||
references:
|
||||
- https://www.fireeye.com/blog/threat-research/2020/10/fin11-email-campaigns-precursor-for-ransomware-data-theft.html
|
||||
- https://blog.virustotal.com/2020/11/keep-your-friends-close-keep-ransomware.html
|
||||
tags:
|
||||
analytic_story:
|
||||
- Clop Ransomware
|
||||
kill_chain_phases:
|
||||
- Exploitation
|
||||
mitre_attack_id:
|
||||
- T1490
|
||||
product:
|
||||
- Splunk Enterprise
|
||||
- Splunk Enterprise Security
|
||||
- Splunk Cloud
|
||||
required_fields:
|
||||
- Processes.process
|
||||
- Process.parent_process_name
|
||||
- _time
|
||||
- Processes.process_name
|
||||
- Processes.parent_process
|
||||
- Processes.dest
|
||||
- Processes.user
|
||||
security_domain: endpoint
|
||||
automated_detection_testing: passed
|
||||
dataset:
|
||||
- https://media.githubusercontent.com/media/splunk/attack_data/master/datasets/malware/clop/clop_a/windows-sysmon.log
|
||||
@@ -47,7 +47,7 @@ search: '| from read_ssa_enriched_events() | eval timestamp=parse_long(ucast(map
|
||||
OR process_name="pcalua.exe" OR process_name="cmdkey.exe" OR process_name="msconfig.exe")
|
||||
|
||||
| eval start_time = timestamp, end_time = timestamp, entities = mvappend(dest_device_id,
|
||||
dest_user_id), body = "TBD" | into write_ssa_detected_events();'
|
||||
dest_user_id), body = "TBD" | into write_null();'
|
||||
how_to_implement: Collect endpoint data such as sysmon or 4688 events.
|
||||
known_false_positives: 'Some custom tools used by admins could be used rarely to launch
|
||||
remotely applications. This might trigger false positives at the beginning when
|
||||
|
||||
@@ -38,7 +38,8 @@ tags:
|
||||
kill_chain_phases:
|
||||
- Exploitation
|
||||
mitre_attack_id:
|
||||
- T1127, T1036.003
|
||||
- T1127
|
||||
- T1036.003
|
||||
nist:
|
||||
- PR.PT
|
||||
- DE.CM
|
||||
|
||||
@@ -28,6 +28,7 @@ tags:
|
||||
analytic_story:
|
||||
- Windows Log Manipulation
|
||||
- Ransomware
|
||||
- Clop Ransomware
|
||||
asset_type: ''
|
||||
automated_detection_testing: passed
|
||||
cis20:
|
||||
|
||||
@@ -20,6 +20,7 @@ tags:
|
||||
analytic_story:
|
||||
- Windows Log Manipulation
|
||||
- Ransomware
|
||||
- Clop Ransomware
|
||||
asset_type: Endpoint
|
||||
automated_detection_testing: passed
|
||||
cis20:
|
||||
|
||||
+8
-13
@@ -1,12 +1,14 @@
|
||||
# Splunk Security Content
|
||||

|
||||
# Splunk Security Content
|
||||

|
||||
|
||||
Welcome to the Splunk Security Content
|
||||
|
||||
This project gives you access to our repository of Analytic Stories that are security guides which provide background on TTPs, mapped to the MITRE framework, the Lockheed Martin Kill Chain, and CIS controls. They include Splunk searches, machine-learning algorithms, and Splunk Phantom playbooks (where available)—all designed to work together to detect, investigate, and respond to threats.
|
||||
|
||||
## View Our Content
|
||||
You can review our Analytic Stories by category [here](stories_categories.md), or in our [Splunk App](https://github.com/splunk/security_content/releases).
|
||||
|
||||
* [Analytic Stories](docs/stories.md)
|
||||
* [Detections](docs/detections.md)
|
||||
|
||||
If you prefer working with the command line, check out our [API](https://docs.splunkresearch.com/?version=latest):
|
||||
|
||||
@@ -17,15 +19,11 @@ curl -s https://content.splunkresearch.com | jq
|
||||
}
|
||||
```
|
||||
|
||||
## Getting Started
|
||||
|
||||
Once you've installed our [app](https://github.com/splunk/security_content/releases), we recommend using our Analytic Story Execution App [(ASX)](https://github.com/splunk/analytics_story_execution) to execute and schedule all of the detections a story automatically.
|
||||
|
||||
## Test Out The Detections
|
||||
The [attack_range](https://github.com/splunk/attack_range) project allows you to spin up an enviroment and launch attacks against it to test the detections.
|
||||
The [attack_range](https://github.com/splunk/attack_range) project allows you to spin up an enviroment and launch attacks against it to test the detections.
|
||||
|
||||
## Questions?
|
||||
If you get stuck or need help with any of our tools, see our [support options](https://github.com/splunk/security_content#support).
|
||||
If you get stuck or need help with any of our tools, see our [support options](https://github.com/splunk/security_content#support).
|
||||
|
||||
## Contribute Content
|
||||
If you want to help the rest of the security community by sharing your own detections, see our [contributor guide](https://github.com/splunk/security_content/blob/develop/docs/CONTRIBUTING.md). Digital defenders unite!
|
||||
@@ -39,7 +37,7 @@ If you want to help the rest of the security community by sharing your own detec
|
||||
* [baselines/](https://github.com/splunk/security_content/tree/develop/baselines): Splunk Phantom and Splunk Enterprise baseline searches needed to support detection searches in Analytic Stories
|
||||
|
||||
#### Content Spec Files
|
||||
* [stories](https://github.com/splunk/security_content/blob/develop/docs/spec/stories.spec.md)
|
||||
* [stories](https://github.com/splunk/security_content/blob/develop/docs/spec/stories.spec.md)
|
||||
* [detections](https://github.com/splunk/security_content/blob/develop/docs/spec/detections.spec.md)
|
||||
* [deployments](https://github.com/splunk/security_content/blob/develop/docs/spec/deployments.spec.md)
|
||||
* [responses](https://github.com/splunk/security_content/blob/develop/docs/spec/responses.spec.md)
|
||||
@@ -47,6 +45,3 @@ If you want to help the rest of the security community by sharing your own detec
|
||||
* [baselines](https://github.com/splunk/security_content/blob/develop/docs/spec/baselines.spec.md)
|
||||
* [lookups](https://github.com/splunk/security_content/blob/develop/docs/spec/lookups.spec.md)
|
||||
* [macros](https://github.com/splunk/security_content/blob/develop/docs/spec/macros.spec.md)
|
||||
|
||||
|
||||
|
||||
|
||||
+27645
File diff suppressed because it is too large
Load Diff
+25200
File diff suppressed because it is too large
Load Diff
@@ -40,6 +40,8 @@
|
||||
|
||||
### Arrays
|
||||
|
||||
* [Untitled array in Baseline Schema](./baselines-properties-datamodel.md "datamodel used in the search") – `#/properties/datamodel#/properties/datamodel`
|
||||
|
||||
* [Untitled array in Detection Schema](./detections-properties-references.md "A list of references for this detection") – `#/properties/references#/properties/references`
|
||||
|
||||
* [Untitled array in Macro Manifest](./macros-properties-arguments.md "A list of the arguments being passed to this macro") – `https://api.splunkresearch.com/schemas/macros.json#/properties/arguments`
|
||||
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Baseline Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/author#/properties/author
|
||||
```
|
||||
|
||||
Author of the baseline
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [baselines.spec.json*](../../out/baselines.spec.json "open original schema") |
|
||||
|
||||
## author Type
|
||||
|
||||
`string`
|
||||
|
||||
## author Examples
|
||||
|
||||
```yaml
|
||||
Bahvin Patel, Splunk
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Baseline Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/date#/properties/date
|
||||
```
|
||||
|
||||
date of creation or modification, format yyyy-mm-dd
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [baselines.spec.json*](../../out/baselines.spec.json "open original schema") |
|
||||
|
||||
## date Type
|
||||
|
||||
`string`
|
||||
|
||||
## date Examples
|
||||
|
||||
```yaml
|
||||
'2019-12-06'
|
||||
|
||||
```
|
||||
@@ -1,26 +0,0 @@
|
||||
# Untitled string in Baseline Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/description#/properties/description
|
||||
```
|
||||
|
||||
A detailed description of the baseline
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [baselines.spec.json*](../../out/baselines.spec.json "open original schema") |
|
||||
|
||||
## description Type
|
||||
|
||||
`string`
|
||||
|
||||
## description Examples
|
||||
|
||||
```yaml
|
||||
>-
|
||||
This search looks for CloudTrail events where an AWS instance is started and
|
||||
creates a baseline of most recent time (latest) and the first time (earliest)
|
||||
we've seen this region in our dataset grouped by the value awsRegion for the
|
||||
last 30 days
|
||||
|
||||
```
|
||||
@@ -1,24 +0,0 @@
|
||||
# Untitled string in Baseline Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/how_to_implement#/properties/how_to_implement
|
||||
```
|
||||
|
||||
information about how to implement. Only needed for non standard implementations.
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [baselines.spec.json*](../../out/baselines.spec.json "open original schema") |
|
||||
|
||||
## how_to_implement Type
|
||||
|
||||
`string`
|
||||
|
||||
## how_to_implement Examples
|
||||
|
||||
```yaml
|
||||
>-
|
||||
This search requires Sysmon Logs and a Sysmon configuration, which includes
|
||||
EventCode 10 for lsass.exe.
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Baseline Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/id#/properties/id
|
||||
```
|
||||
|
||||
UUID as unique identifier
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [baselines.spec.json*](../../out/baselines.spec.json "open original schema") |
|
||||
|
||||
## id Type
|
||||
|
||||
`string`
|
||||
|
||||
## id Examples
|
||||
|
||||
```yaml
|
||||
fc0edc95-ff2b-48b0-9f6f-63da3789fd63
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Name of baseline Schema
|
||||
|
||||
```txt
|
||||
#/properties/name#/properties/name
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [baselines.spec.json*](../../out/baselines.spec.json "open original schema") |
|
||||
|
||||
## name Type
|
||||
|
||||
`string` ([Name of baseline](baselines-properties-name-of-baseline.md))
|
||||
|
||||
## name Examples
|
||||
|
||||
```yaml
|
||||
Previously Seen AWS Regions
|
||||
|
||||
```
|
||||
@@ -1,24 +0,0 @@
|
||||
# Untitled string in Baseline Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/search#/properties/search
|
||||
```
|
||||
|
||||
The Splunk search for the baseline
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [baselines.spec.json*](../../out/baselines.spec.json "open original schema") |
|
||||
|
||||
## search Type
|
||||
|
||||
`string`
|
||||
|
||||
## search Examples
|
||||
|
||||
```yaml
|
||||
>-
|
||||
cloudtrail StartInstances | stats earliest(_time) as earliest latest(_time) as
|
||||
latest by awsRegion | outputlookup previously_seen_aws_regions.csv
|
||||
|
||||
```
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled undefined type in Baseline Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/tags#/properties/tags/default
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [baselines.spec.json*](../../out/baselines.spec.json "open original schema") |
|
||||
|
||||
## default Type
|
||||
|
||||
unknown
|
||||
@@ -1,47 +0,0 @@
|
||||
# Untitled object in Baseline Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/tags#/properties/tags
|
||||
```
|
||||
|
||||
An array of key value pairs for tagging
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [baselines.spec.json*](../../out/baselines.spec.json "open original schema") |
|
||||
|
||||
## tags Type
|
||||
|
||||
`object` ([Details](baselines-properties-tags.md))
|
||||
|
||||
## tags Constraints
|
||||
|
||||
**minimum number of items**: the minimum number of items for this array is: `1`
|
||||
|
||||
**unique items**: all items in this array must be unique. Duplicates are not allowed.
|
||||
|
||||
## tags Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
{}
|
||||
```
|
||||
|
||||
## tags Examples
|
||||
|
||||
```yaml
|
||||
analytic_story: suspicious_aws_ec2_activities
|
||||
custom_key: custom_value
|
||||
|
||||
```
|
||||
|
||||
# tags Properties
|
||||
|
||||
| Property | Type | Required | Nullable | Defined by |
|
||||
| :-------------------- | :--- | :------- | :---------- | :--------- |
|
||||
| Additional Properties | Any | Optional | can be null | |
|
||||
|
||||
## Additional Properties
|
||||
|
||||
Additional properties are allowed and do not have to follow a specific schema
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled integer in Baseline Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/version#/properties/version
|
||||
```
|
||||
|
||||
version of baseline, e.g. 1 or 2 ...
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [baselines.spec.json*](../../out/baselines.spec.json "open original schema") |
|
||||
|
||||
## version Type
|
||||
|
||||
`integer`
|
||||
|
||||
## version Examples
|
||||
|
||||
```yaml
|
||||
1
|
||||
|
||||
```
|
||||
+29
-3
@@ -6,9 +6,9 @@ http://example.com/example.json
|
||||
|
||||
schema for baselines
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :-------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [baselines.spec.json](../../out/baselines.spec.json "open original schema") |
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [baselines.spec.json](../../spec/baselines.spec.json "open original schema") |
|
||||
|
||||
## Baseline Schema Type
|
||||
|
||||
@@ -26,6 +26,7 @@ schema for baselines
|
||||
| [name](#name) | `string` | Required | cannot be null | [Baseline Schema](baselines-properties-name-of-baseline.md "#/properties/name#/properties/name") |
|
||||
| [search](#search) | `string` | Required | cannot be null | [Baseline Schema](baselines-properties-search.md "#/properties/search#/properties/search") |
|
||||
| [tags](#tags) | `object` | Required | cannot be null | [Baseline Schema](baselines-properties-tags.md "#/properties/tags#/properties/tags") |
|
||||
| [datamodel](#datamodel) | `array` | Optional | cannot be null | [Baseline Schema](baselines-properties-datamodel.md "#/properties/datamodel#/properties/datamodel") |
|
||||
| [version](#version) | `integer` | Required | cannot be null | [Baseline Schema](baselines-properties-version.md "#/properties/version#/properties/version") |
|
||||
| Additional Properties | Any | Optional | can be null | |
|
||||
|
||||
@@ -252,6 +253,31 @@ custom_key: custom_value
|
||||
|
||||
```
|
||||
|
||||
## datamodel
|
||||
|
||||
datamodel used in the search
|
||||
|
||||
`datamodel`
|
||||
|
||||
* is optional
|
||||
|
||||
* Type: `string[]`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Baseline Schema](baselines-properties-datamodel.md "#/properties/datamodel#/properties/datamodel")
|
||||
|
||||
### datamodel Type
|
||||
|
||||
`string[]`
|
||||
|
||||
### datamodel Examples
|
||||
|
||||
```yaml
|
||||
Endpoint
|
||||
|
||||
```
|
||||
|
||||
## version
|
||||
|
||||
version of baseline, e.g. 1 or 2 ...
|
||||
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled undefined type in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
http://example.com/example.json#/default
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## default Type
|
||||
|
||||
unknown
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled undefined type in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action#/properties/alert_action/default
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## default Type
|
||||
|
||||
unknown
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled undefined type in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/email#/properties/alert_action/properties/email/default
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## default Type
|
||||
|
||||
unknown
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/email/properties/message#/properties/alert_action/properties/email/properties/message
|
||||
```
|
||||
|
||||
message of email
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## message Type
|
||||
|
||||
`string`
|
||||
|
||||
## message Examples
|
||||
|
||||
```yaml
|
||||
Splunk Alert $name$ triggered %fields%
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/email/properties/subject#/properties/alert_action/properties/email/properties/subject
|
||||
```
|
||||
|
||||
Subject of email
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## subject Type
|
||||
|
||||
`string`
|
||||
|
||||
## subject Examples
|
||||
|
||||
```yaml
|
||||
Splunk Alert $name$
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/email/properties/to#/properties/alert_action/properties/email/properties/to
|
||||
```
|
||||
|
||||
Recipient of email
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## to Type
|
||||
|
||||
`string`
|
||||
|
||||
## to Examples
|
||||
|
||||
```yaml
|
||||
test@test.com
|
||||
|
||||
```
|
||||
@@ -1,120 +0,0 @@
|
||||
# Untitled object in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/email#/properties/alert_action/properties/email
|
||||
```
|
||||
|
||||
By enabling it, an email is sent with the results
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## email Type
|
||||
|
||||
`object` ([Details](deployments-properties-alert_action-properties-email.md))
|
||||
|
||||
## email Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
{}
|
||||
```
|
||||
|
||||
## email Examples
|
||||
|
||||
```yaml
|
||||
message: Splunk Alert $name$ triggered %fields%
|
||||
subject: Splunk Alert $name$
|
||||
to: test@test.com
|
||||
|
||||
```
|
||||
|
||||
# email Properties
|
||||
|
||||
| Property | Type | Required | Nullable | Defined by |
|
||||
| :-------------------- | :------- | :------- | :------------- | :--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
||||
| [message](#message) | `string` | Required | cannot be null | [Deployment Schema](deployments-properties-alert_action-properties-email-properties-message.md "#/properties/alert_action/properties/email/properties/message#/properties/alert_action/properties/email/properties/message") |
|
||||
| [subject](#subject) | `string` | Required | cannot be null | [Deployment Schema](deployments-properties-alert_action-properties-email-properties-subject.md "#/properties/alert_action/properties/email/properties/subject#/properties/alert_action/properties/email/properties/subject") |
|
||||
| [to](#to) | `string` | Required | cannot be null | [Deployment Schema](deployments-properties-alert_action-properties-email-properties-to.md "#/properties/alert_action/properties/email/properties/to#/properties/alert_action/properties/email/properties/to") |
|
||||
| Additional Properties | Any | Optional | can be null | |
|
||||
|
||||
## message
|
||||
|
||||
message of email
|
||||
|
||||
`message`
|
||||
|
||||
* is required
|
||||
|
||||
* Type: `string`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-alert_action-properties-email-properties-message.md "#/properties/alert_action/properties/email/properties/message#/properties/alert_action/properties/email/properties/message")
|
||||
|
||||
### message Type
|
||||
|
||||
`string`
|
||||
|
||||
### message Examples
|
||||
|
||||
```yaml
|
||||
Splunk Alert $name$ triggered %fields%
|
||||
|
||||
```
|
||||
|
||||
## subject
|
||||
|
||||
Subject of email
|
||||
|
||||
`subject`
|
||||
|
||||
* is required
|
||||
|
||||
* Type: `string`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-alert_action-properties-email-properties-subject.md "#/properties/alert_action/properties/email/properties/subject#/properties/alert_action/properties/email/properties/subject")
|
||||
|
||||
### subject Type
|
||||
|
||||
`string`
|
||||
|
||||
### subject Examples
|
||||
|
||||
```yaml
|
||||
Splunk Alert $name$
|
||||
|
||||
```
|
||||
|
||||
## to
|
||||
|
||||
Recipient of email
|
||||
|
||||
`to`
|
||||
|
||||
* is required
|
||||
|
||||
* Type: `string`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-alert_action-properties-email-properties-to.md "#/properties/alert_action/properties/email/properties/to#/properties/alert_action/properties/email/properties/to")
|
||||
|
||||
### to Type
|
||||
|
||||
`string`
|
||||
|
||||
### to Examples
|
||||
|
||||
```yaml
|
||||
test@test.com
|
||||
|
||||
```
|
||||
|
||||
## Additional Properties
|
||||
|
||||
Additional properties are allowed and do not have to follow a specific schema
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled undefined type in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/index#/properties/alert_action/properties/index/default
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## default Type
|
||||
|
||||
unknown
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/index/properties/name#/properties/alert_action/properties/index/properties/name
|
||||
```
|
||||
|
||||
Name of the index
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## name Type
|
||||
|
||||
`string`
|
||||
|
||||
## name Examples
|
||||
|
||||
```yaml
|
||||
asx
|
||||
|
||||
```
|
||||
@@ -1,66 +0,0 @@
|
||||
# Untitled object in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/index#/properties/alert_action/properties/index
|
||||
```
|
||||
|
||||
By enabling it, the results are stored in another index
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## index Type
|
||||
|
||||
`object` ([Details](deployments-properties-alert_action-properties-index.md))
|
||||
|
||||
## index Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
{}
|
||||
```
|
||||
|
||||
## index Examples
|
||||
|
||||
```yaml
|
||||
name: asx
|
||||
|
||||
```
|
||||
|
||||
# index Properties
|
||||
|
||||
| Property | Type | Required | Nullable | Defined by |
|
||||
| :-------------------- | :------- | :------- | :------------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
|
||||
| [name](#name) | `string` | Required | cannot be null | [Deployment Schema](deployments-properties-alert_action-properties-index-properties-name.md "#/properties/alert_action/properties/index/properties/name#/properties/alert_action/properties/index/properties/name") |
|
||||
| Additional Properties | Any | Optional | can be null | |
|
||||
|
||||
## name
|
||||
|
||||
Name of the index
|
||||
|
||||
`name`
|
||||
|
||||
* is required
|
||||
|
||||
* Type: `string`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-alert_action-properties-index-properties-name.md "#/properties/alert_action/properties/index/properties/name#/properties/alert_action/properties/index/properties/name")
|
||||
|
||||
### name Type
|
||||
|
||||
`string`
|
||||
|
||||
### name Examples
|
||||
|
||||
```yaml
|
||||
asx
|
||||
|
||||
```
|
||||
|
||||
## Additional Properties
|
||||
|
||||
Additional properties are allowed and do not have to follow a specific schema
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled undefined type in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/notable#/properties/alert_action/properties/notable/default
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## default Type
|
||||
|
||||
unknown
|
||||
-22
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/notable/properties/rule_description#/properties/alert_action/properties/notable/properties/rule_description
|
||||
```
|
||||
|
||||
Rule description of the notable event
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## rule_description Type
|
||||
|
||||
`string`
|
||||
|
||||
## rule_description Examples
|
||||
|
||||
```yaml
|
||||
'%description%'
|
||||
|
||||
```
|
||||
-22
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/notable/properties/rule_title#/properties/alert_action/properties/notable/properties/rule_title
|
||||
```
|
||||
|
||||
Rule title of the notable event
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## rule_title Type
|
||||
|
||||
`string`
|
||||
|
||||
## rule_title Examples
|
||||
|
||||
```yaml
|
||||
'%name%'
|
||||
|
||||
```
|
||||
@@ -1,93 +0,0 @@
|
||||
# Untitled object in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action/properties/notable#/properties/alert_action/properties/notable
|
||||
```
|
||||
|
||||
By enabling it, a notable is generated
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## notable Type
|
||||
|
||||
`object` ([Details](deployments-properties-alert_action-properties-notable.md))
|
||||
|
||||
## notable Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
{}
|
||||
```
|
||||
|
||||
## notable Examples
|
||||
|
||||
```yaml
|
||||
rule_description: '%description%'
|
||||
rule_title: '%name%'
|
||||
|
||||
```
|
||||
|
||||
# notable Properties
|
||||
|
||||
| Property | Type | Required | Nullable | Defined by |
|
||||
| :------------------------------------ | :------- | :------- | :------------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
|
||||
| [rule_description](#rule_description) | `string` | Required | cannot be null | [Deployment Schema](deployments-properties-alert_action-properties-notable-properties-rule_description.md "#/properties/alert_action/properties/notable/properties/rule_description#/properties/alert_action/properties/notable/properties/rule_description") |
|
||||
| [rule_title](#rule_title) | `string` | Required | cannot be null | [Deployment Schema](deployments-properties-alert_action-properties-notable-properties-rule_title.md "#/properties/alert_action/properties/notable/properties/rule_title#/properties/alert_action/properties/notable/properties/rule_title") |
|
||||
| Additional Properties | Any | Optional | can be null | |
|
||||
|
||||
## rule_description
|
||||
|
||||
Rule description of the notable event
|
||||
|
||||
`rule_description`
|
||||
|
||||
* is required
|
||||
|
||||
* Type: `string`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-alert_action-properties-notable-properties-rule_description.md "#/properties/alert_action/properties/notable/properties/rule_description#/properties/alert_action/properties/notable/properties/rule_description")
|
||||
|
||||
### rule_description Type
|
||||
|
||||
`string`
|
||||
|
||||
### rule_description Examples
|
||||
|
||||
```yaml
|
||||
'%description%'
|
||||
|
||||
```
|
||||
|
||||
## rule_title
|
||||
|
||||
Rule title of the notable event
|
||||
|
||||
`rule_title`
|
||||
|
||||
* is required
|
||||
|
||||
* Type: `string`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-alert_action-properties-notable-properties-rule_title.md "#/properties/alert_action/properties/notable/properties/rule_title#/properties/alert_action/properties/notable/properties/rule_title")
|
||||
|
||||
### rule_title Type
|
||||
|
||||
`string`
|
||||
|
||||
### rule_title Examples
|
||||
|
||||
```yaml
|
||||
'%name%'
|
||||
|
||||
```
|
||||
|
||||
## Additional Properties
|
||||
|
||||
Additional properties are allowed and do not have to follow a specific schema
|
||||
@@ -1,153 +0,0 @@
|
||||
# Untitled object in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/alert_action#/properties/alert_action
|
||||
```
|
||||
|
||||
Set alert action parameter for search
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## alert_action Type
|
||||
|
||||
`object` ([Details](deployments-properties-alert_action.md))
|
||||
|
||||
## alert_action Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
{}
|
||||
```
|
||||
|
||||
## alert_action Examples
|
||||
|
||||
```yaml
|
||||
email:
|
||||
message: Splunk Alert $name$ triggered %fields%
|
||||
subject: Splunk Alert $name$
|
||||
to: test@test.com
|
||||
index:
|
||||
name: asx
|
||||
notable:
|
||||
rule_description: '%description%'
|
||||
rule_title: '%name%'
|
||||
|
||||
```
|
||||
|
||||
# alert_action Properties
|
||||
|
||||
| Property | Type | Required | Nullable | Defined by |
|
||||
| :-------------------- | :------- | :------- | :------------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
|
||||
| [email](#email) | `object` | Optional | cannot be null | [Deployment Schema](deployments-properties-alert_action-properties-email.md "#/properties/alert_action/properties/email#/properties/alert_action/properties/email") |
|
||||
| [index](#index) | `object` | Optional | cannot be null | [Deployment Schema](deployments-properties-alert_action-properties-index.md "#/properties/alert_action/properties/index#/properties/alert_action/properties/index") |
|
||||
| [notable](#notable) | `object` | Optional | cannot be null | [Deployment Schema](deployments-properties-alert_action-properties-notable.md "#/properties/alert_action/properties/notable#/properties/alert_action/properties/notable") |
|
||||
| Additional Properties | Any | Optional | can be null | |
|
||||
|
||||
## email
|
||||
|
||||
By enabling it, an email is sent with the results
|
||||
|
||||
`email`
|
||||
|
||||
* is optional
|
||||
|
||||
* Type: `object` ([Details](deployments-properties-alert_action-properties-email.md))
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-alert_action-properties-email.md "#/properties/alert_action/properties/email#/properties/alert_action/properties/email")
|
||||
|
||||
### email Type
|
||||
|
||||
`object` ([Details](deployments-properties-alert_action-properties-email.md))
|
||||
|
||||
### email Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
{}
|
||||
```
|
||||
|
||||
### email Examples
|
||||
|
||||
```yaml
|
||||
message: Splunk Alert $name$ triggered %fields%
|
||||
subject: Splunk Alert $name$
|
||||
to: test@test.com
|
||||
|
||||
```
|
||||
|
||||
## index
|
||||
|
||||
By enabling it, the results are stored in another index
|
||||
|
||||
`index`
|
||||
|
||||
* is optional
|
||||
|
||||
* Type: `object` ([Details](deployments-properties-alert_action-properties-index.md))
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-alert_action-properties-index.md "#/properties/alert_action/properties/index#/properties/alert_action/properties/index")
|
||||
|
||||
### index Type
|
||||
|
||||
`object` ([Details](deployments-properties-alert_action-properties-index.md))
|
||||
|
||||
### index Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
{}
|
||||
```
|
||||
|
||||
### index Examples
|
||||
|
||||
```yaml
|
||||
name: asx
|
||||
|
||||
```
|
||||
|
||||
## notable
|
||||
|
||||
By enabling it, a notable is generated
|
||||
|
||||
`notable`
|
||||
|
||||
* is optional
|
||||
|
||||
* Type: `object` ([Details](deployments-properties-alert_action-properties-notable.md))
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-alert_action-properties-notable.md "#/properties/alert_action/properties/notable#/properties/alert_action/properties/notable")
|
||||
|
||||
### notable Type
|
||||
|
||||
`object` ([Details](deployments-properties-alert_action-properties-notable.md))
|
||||
|
||||
### notable Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
{}
|
||||
```
|
||||
|
||||
### notable Examples
|
||||
|
||||
```yaml
|
||||
rule_description: '%description%'
|
||||
rule_title: '%name%'
|
||||
|
||||
```
|
||||
|
||||
## Additional Properties
|
||||
|
||||
Additional properties are allowed and do not have to follow a specific schema
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled undefined type in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/scheduling#/properties/scheduling/default
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## default Type
|
||||
|
||||
unknown
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/scheduling/properties/cron_schedule#/properties/scheduling/properties/cron_schedule
|
||||
```
|
||||
|
||||
Cron schedule to schedule the Splunk searches.
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## cron_schedule Type
|
||||
|
||||
`string`
|
||||
|
||||
## cron_schedule Examples
|
||||
|
||||
```yaml
|
||||
'*/10 * * * *'
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/scheduling/properties/earliest_time#/properties/scheduling/properties/earliest_time
|
||||
```
|
||||
|
||||
earliest time of search
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## earliest_time Type
|
||||
|
||||
`string`
|
||||
|
||||
## earliest_time Examples
|
||||
|
||||
```yaml
|
||||
'-10m'
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/scheduling/properties/latest_time#/properties/scheduling/properties/latest_time
|
||||
```
|
||||
|
||||
latest time of search
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## latest_time Type
|
||||
|
||||
`string`
|
||||
|
||||
## latest_time Examples
|
||||
|
||||
```yaml
|
||||
now
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/scheduling/properties/schedule_window#/properties/scheduling/properties/schedule_window
|
||||
```
|
||||
|
||||
schedule window for search
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## schedule_window Type
|
||||
|
||||
`string`
|
||||
|
||||
## schedule_window Examples
|
||||
|
||||
```yaml
|
||||
auto
|
||||
|
||||
```
|
||||
@@ -1,147 +0,0 @@
|
||||
# Untitled object in Deployment Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/scheduling#/properties/scheduling
|
||||
```
|
||||
|
||||
allows to set scheduling parameter
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [deployments.spec.json*](../../out/deployments.spec.json "open original schema") |
|
||||
|
||||
## scheduling Type
|
||||
|
||||
`object` ([Details](deployments-properties-scheduling.md))
|
||||
|
||||
## scheduling Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
{}
|
||||
```
|
||||
|
||||
## scheduling Examples
|
||||
|
||||
```yaml
|
||||
cron_schedule: '*/10 * * * *'
|
||||
earliest_time: '-10m'
|
||||
latest_time: now
|
||||
schedule_window: auto
|
||||
|
||||
```
|
||||
|
||||
# scheduling Properties
|
||||
|
||||
| Property | Type | Required | Nullable | Defined by |
|
||||
| :---------------------------------- | :------- | :------- | :------------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
|
||||
| [cron_schedule](#cron_schedule) | `string` | Required | cannot be null | [Deployment Schema](deployments-properties-scheduling-properties-cron_schedule.md "#/properties/scheduling/properties/cron_schedule#/properties/scheduling/properties/cron_schedule") |
|
||||
| [earliest_time](#earliest_time) | `string` | Required | cannot be null | [Deployment Schema](deployments-properties-scheduling-properties-earliest_time.md "#/properties/scheduling/properties/earliest_time#/properties/scheduling/properties/earliest_time") |
|
||||
| [latest_time](#latest_time) | `string` | Required | cannot be null | [Deployment Schema](deployments-properties-scheduling-properties-latest_time.md "#/properties/scheduling/properties/latest_time#/properties/scheduling/properties/latest_time") |
|
||||
| [schedule_window](#schedule_window) | `string` | Optional | cannot be null | [Deployment Schema](deployments-properties-scheduling-properties-schedule_window.md "#/properties/scheduling/properties/schedule_window#/properties/scheduling/properties/schedule_window") |
|
||||
| Additional Properties | Any | Optional | can be null | |
|
||||
|
||||
## cron_schedule
|
||||
|
||||
Cron schedule to schedule the Splunk searches.
|
||||
|
||||
`cron_schedule`
|
||||
|
||||
* is required
|
||||
|
||||
* Type: `string`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-scheduling-properties-cron_schedule.md "#/properties/scheduling/properties/cron_schedule#/properties/scheduling/properties/cron_schedule")
|
||||
|
||||
### cron_schedule Type
|
||||
|
||||
`string`
|
||||
|
||||
### cron_schedule Examples
|
||||
|
||||
```yaml
|
||||
'*/10 * * * *'
|
||||
|
||||
```
|
||||
|
||||
## earliest_time
|
||||
|
||||
earliest time of search
|
||||
|
||||
`earliest_time`
|
||||
|
||||
* is required
|
||||
|
||||
* Type: `string`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-scheduling-properties-earliest_time.md "#/properties/scheduling/properties/earliest_time#/properties/scheduling/properties/earliest_time")
|
||||
|
||||
### earliest_time Type
|
||||
|
||||
`string`
|
||||
|
||||
### earliest_time Examples
|
||||
|
||||
```yaml
|
||||
'-10m'
|
||||
|
||||
```
|
||||
|
||||
## latest_time
|
||||
|
||||
latest time of search
|
||||
|
||||
`latest_time`
|
||||
|
||||
* is required
|
||||
|
||||
* Type: `string`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-scheduling-properties-latest_time.md "#/properties/scheduling/properties/latest_time#/properties/scheduling/properties/latest_time")
|
||||
|
||||
### latest_time Type
|
||||
|
||||
`string`
|
||||
|
||||
### latest_time Examples
|
||||
|
||||
```yaml
|
||||
now
|
||||
|
||||
```
|
||||
|
||||
## schedule_window
|
||||
|
||||
schedule window for search
|
||||
|
||||
`schedule_window`
|
||||
|
||||
* is optional
|
||||
|
||||
* Type: `string`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Deployment Schema](deployments-properties-scheduling-properties-schedule_window.md "#/properties/scheduling/properties/schedule_window#/properties/scheduling/properties/schedule_window")
|
||||
|
||||
### schedule_window Type
|
||||
|
||||
`string`
|
||||
|
||||
### schedule_window Examples
|
||||
|
||||
```yaml
|
||||
auto
|
||||
|
||||
```
|
||||
|
||||
## Additional Properties
|
||||
|
||||
Additional properties are allowed and do not have to follow a specific schema
|
||||
@@ -6,9 +6,9 @@ http://example.com/example.json
|
||||
|
||||
schema for deployment
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------ |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [deployments.spec.json](../../out/deployments.spec.json "open original schema") |
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [deployments.spec.json](../../spec/deployments.spec.json "open original schema") |
|
||||
|
||||
## Deployment Schema Type
|
||||
|
||||
|
||||
@@ -1,24 +0,0 @@
|
||||
# Untitled string in Detection Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/knwon_false_positives#/properties/known_false_positives
|
||||
```
|
||||
|
||||
known false postives
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [detections.spec.json*](../../out/detections.spec.json "open original schema") |
|
||||
|
||||
## known_false_positives Type
|
||||
|
||||
`string`
|
||||
|
||||
## known_false_positives Examples
|
||||
|
||||
```yaml
|
||||
>-
|
||||
Administrators can create memory dumps for debugging purposes, but memory
|
||||
dumps of the LSASS process would be unusual.
|
||||
|
||||
```
|
||||
@@ -1,23 +0,0 @@
|
||||
# The Items Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/references/items#/properties/references/items
|
||||
```
|
||||
|
||||
An explanation about the purpose of this instance.
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [detections.spec.json*](../../out/detections.spec.json "open original schema") |
|
||||
|
||||
## items Type
|
||||
|
||||
`string` ([The Items Schema](detections-properties-references-the-items-schema.md))
|
||||
|
||||
## items Examples
|
||||
|
||||
```yaml
|
||||
>-
|
||||
https://2017.zeronights.org/wp-content/uploads/materials/ZN17_Kheirkhabarov_Hunting_for_Credentials_Dumping_in_Windows_Environment.pdf
|
||||
|
||||
```
|
||||
@@ -1,31 +0,0 @@
|
||||
# Untitled array in Detection Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/references#/properties/references
|
||||
```
|
||||
|
||||
A list of references for this detection
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [detections.spec.json*](../../out/detections.spec.json "open original schema") |
|
||||
|
||||
## references Type
|
||||
|
||||
`string[]` ([The Items Schema](detections-properties-references-the-items-schema.md))
|
||||
|
||||
## references Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
[]
|
||||
```
|
||||
|
||||
## references Examples
|
||||
|
||||
```yaml
|
||||
- >-
|
||||
https://2017.zeronights.org/wp-content/uploads/materials/ZN17_Kheirkhabarov_Hunting_for_Credentials_Dumping_in_Windows_Environment.pdf
|
||||
|
||||
```
|
||||
@@ -1,24 +0,0 @@
|
||||
# Untitled string in Detection Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/type#/properties/type/items
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [detections.spec.json*](../../out/detections.spec.json "open original schema") |
|
||||
|
||||
## items Type
|
||||
|
||||
`string`
|
||||
|
||||
## items Constraints
|
||||
|
||||
**enum**: the value of this property must be equal to one of the following values:
|
||||
|
||||
| Value | Explanation |
|
||||
| :------------ | :---------- |
|
||||
| `"batch"` | |
|
||||
| `"streaming"` | |
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Detection Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/type#/properties/type
|
||||
```
|
||||
|
||||
type of detection
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [detections.spec.json*](../../out/detections.spec.json "open original schema") |
|
||||
|
||||
## type Type
|
||||
|
||||
`string`
|
||||
|
||||
## type Examples
|
||||
|
||||
```yaml
|
||||
streaming
|
||||
|
||||
```
|
||||
+29
-3
@@ -6,9 +6,9 @@ http://example.com/example.json
|
||||
|
||||
schema for detections
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :---------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [detections.spec.json](../../out/detections.spec.json "open original schema") |
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [detections.spec.json](../../spec/detections.spec.json "open original schema") |
|
||||
|
||||
## Detection Schema Type
|
||||
|
||||
@@ -29,6 +29,7 @@ schema for detections
|
||||
| [search](#search) | `string` | Required | cannot be null | [Detection Schema](detections-properties-search.md "#/properties/search#/properties/search") |
|
||||
| [tags](#tags) | `object` | Required | cannot be null | [Detection Schema](detections-properties-tags.md "#/properties/tags#/properties/tags") |
|
||||
| [type](#type) | `string` | Required | cannot be null | [Detection Schema](detections-properties-type.md "#/properties/type#/properties/type") |
|
||||
| [datamodel](#datamodel) | `array` | Optional | cannot be null | [Detection Schema](detections-properties-datamodel.md "#/properties/datamodel#/properties/datamodel") |
|
||||
| [version](#version) | `integer` | Required | cannot be null | [Detection Schema](detections-properties-version.md "#/properties/version#/properties/version") |
|
||||
| Additional Properties | Any | Optional | can be null | |
|
||||
|
||||
@@ -354,6 +355,31 @@ streaming
|
||||
|
||||
```
|
||||
|
||||
## datamodel
|
||||
|
||||
datamodel used in the search
|
||||
|
||||
`datamodel`
|
||||
|
||||
* is optional
|
||||
|
||||
* Type: `string[]`
|
||||
|
||||
* cannot be null
|
||||
|
||||
* defined in: [Detection Schema](detections-properties-datamodel.md "#/properties/datamodel#/properties/datamodel")
|
||||
|
||||
### datamodel Type
|
||||
|
||||
`string[]`
|
||||
|
||||
### datamodel Examples
|
||||
|
||||
```yaml
|
||||
Endpoint
|
||||
|
||||
```
|
||||
|
||||
## version
|
||||
|
||||
version of detection, e.g. 1 or 2 ...
|
||||
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled undefined type in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/oneOf/0
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## 0 Type
|
||||
|
||||
unknown
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled undefined type in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/oneOf/1
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## 1 Type
|
||||
|
||||
unknown
|
||||
@@ -1,31 +0,0 @@
|
||||
# Untitled string in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/properties/case_sensitive_match
|
||||
```
|
||||
|
||||
What the macro is intended to filter
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## case_sensitive_match Type
|
||||
|
||||
`string`
|
||||
|
||||
## case_sensitive_match Constraints
|
||||
|
||||
**enum**: the value of this property must be equal to one of the following values:
|
||||
|
||||
| Value | Explanation |
|
||||
| :-------- | :---------- |
|
||||
| `"true"` | |
|
||||
| `"false"` | |
|
||||
|
||||
## case_sensitive_match Examples
|
||||
|
||||
```yaml
|
||||
'true'
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/properties/collection
|
||||
```
|
||||
|
||||
Name of the collection to use for this lookup
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## collection Type
|
||||
|
||||
`string`
|
||||
|
||||
## collection Examples
|
||||
|
||||
```yaml
|
||||
prohibited_apps_launching_cmd
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/properties/default_match
|
||||
```
|
||||
|
||||
The default value if no match is found
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## default_match Type
|
||||
|
||||
`string`
|
||||
|
||||
## default_match Examples
|
||||
|
||||
```yaml
|
||||
'true'
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/properties/description
|
||||
```
|
||||
|
||||
The description of this lookup
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## description Type
|
||||
|
||||
`string`
|
||||
|
||||
## description Examples
|
||||
|
||||
```yaml
|
||||
This lookup contains file names that exist in the Windows\System32 directory
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/properties/fields_list
|
||||
```
|
||||
|
||||
A comma and space separated list of field names
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## fields_list Type
|
||||
|
||||
`string`
|
||||
|
||||
## fields_list Examples
|
||||
|
||||
```yaml
|
||||
_key, dest, process_name
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/properties/filename
|
||||
```
|
||||
|
||||
The name of the file to use for this lookup
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## filename Type
|
||||
|
||||
`string`
|
||||
|
||||
## filename Examples
|
||||
|
||||
```yaml
|
||||
prohibited_apps_launching_cmd.csv
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/properties/filter
|
||||
```
|
||||
|
||||
Use this attribute to improve search performance when working with significantly large KV
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## filter Type
|
||||
|
||||
`string`
|
||||
|
||||
## filter Examples
|
||||
|
||||
```yaml
|
||||
dest="SPLK_*"
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/properties/match_type
|
||||
```
|
||||
|
||||
A comma and space-delimited list of \<match_type>(\<field_name>) specification to allow for non-exact matching
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## match_type Type
|
||||
|
||||
`string`
|
||||
|
||||
## match_type Examples
|
||||
|
||||
```yaml
|
||||
WILDCARD(process)
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled integer in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/properties/max_matches
|
||||
```
|
||||
|
||||
The maximum number of possible matches for each input lookup value
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## max_matches Type
|
||||
|
||||
`integer`
|
||||
|
||||
## max_matches Examples
|
||||
|
||||
```yaml
|
||||
'100'
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled integer in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/properties/min_matches
|
||||
```
|
||||
|
||||
Minimum number of possible matches for each input lookup value
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## min_matches Type
|
||||
|
||||
`integer`
|
||||
|
||||
## min_matches Examples
|
||||
|
||||
```yaml
|
||||
'1'
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Lookup Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/lookups.json#/properties/name
|
||||
```
|
||||
|
||||
The name of the lookup to be used in searches
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [lookups.spec.json*](../../out/lookups.spec.json "open original schema") |
|
||||
|
||||
## name Type
|
||||
|
||||
`string`
|
||||
|
||||
## name Examples
|
||||
|
||||
```yaml
|
||||
isWindowsSystemFile_lookup
|
||||
|
||||
```
|
||||
@@ -6,9 +6,9 @@ https://api.splunkresearch.com/schemas/lookups.json
|
||||
|
||||
A object that defines a lookup file and its properties.
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :---------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [lookups.spec.json](../../out/lookups.spec.json "open original schema") |
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :----------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [lookups.spec.json](../../spec/lookups.spec.json "open original schema") |
|
||||
|
||||
## Lookup Manifest Type
|
||||
|
||||
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled string in Macro Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/macros.json#/properties/arguments/items
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [macros.spec.json*](../../out/macros.spec.json "open original schema") |
|
||||
|
||||
## items Type
|
||||
|
||||
`string`
|
||||
@@ -1,21 +0,0 @@
|
||||
# Untitled array in Macro Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/macros.json#/properties/arguments
|
||||
```
|
||||
|
||||
A list of the arguments being passed to this macro
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [macros.spec.json*](../../out/macros.spec.json "open original schema") |
|
||||
|
||||
## arguments Type
|
||||
|
||||
`string[]`
|
||||
|
||||
## arguments Constraints
|
||||
|
||||
**minimum number of items**: the minimum number of items for this array is: `0`
|
||||
|
||||
**unique items**: all items in this array must be unique. Duplicates are not allowed.
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Macro Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/macros.json#/properties/definition
|
||||
```
|
||||
|
||||
The macro definition
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [macros.spec.json*](../../out/macros.spec.json "open original schema") |
|
||||
|
||||
## definition Type
|
||||
|
||||
`string`
|
||||
|
||||
## definition Examples
|
||||
|
||||
```yaml
|
||||
(query=fls-na* AND query = www* AND query=images*)
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Macro Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/macros.json#/properties/description
|
||||
```
|
||||
|
||||
What the macro is intended to filter
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [macros.spec.json*](../../out/macros.spec.json "open original schema") |
|
||||
|
||||
## description Type
|
||||
|
||||
`string`
|
||||
|
||||
## description Examples
|
||||
|
||||
```yaml
|
||||
Use this macro to filter out known good objects
|
||||
|
||||
```
|
||||
@@ -1,22 +0,0 @@
|
||||
# Untitled string in Macro Manifest Schema
|
||||
|
||||
```txt
|
||||
https://api.splunkresearch.com/schemas/macros.json#/properties/name
|
||||
```
|
||||
|
||||
The name of the macro
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [macros.spec.json*](../../out/macros.spec.json "open original schema") |
|
||||
|
||||
## name Type
|
||||
|
||||
`string`
|
||||
|
||||
## name Examples
|
||||
|
||||
```yaml
|
||||
detection_search_output_filter
|
||||
|
||||
```
|
||||
+3
-3
@@ -6,9 +6,9 @@ https://api.splunkresearch.com/schemas/macros.json
|
||||
|
||||
An object that defines the parameters for a Splunk Macro
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :-------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [macros.spec.json](../../out/macros.spec.json "open original schema") |
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :----------- | :---------------- | :-------------------- | :------------------ | :--------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | No | Forbidden | Allowed | none | [macros.spec.json](../../spec/macros.spec.json "open original schema") |
|
||||
|
||||
## Macro Manifest Type
|
||||
|
||||
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled undefined type in Response Schema Schema
|
||||
|
||||
```txt
|
||||
https://raw.githubusercontent.com/splunk/security_content/develop/docs/spec/response_tasks.spec.json#/default
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [response_tasks.spec.json*](../../out/response_tasks.spec.json "open original schema") |
|
||||
|
||||
## default Type
|
||||
|
||||
unknown
|
||||
@@ -1,15 +0,0 @@
|
||||
# Untitled undefined type in Response Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/automation#/properties/automation/default
|
||||
```
|
||||
|
||||
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [response_tasks.spec.json*](../../out/response_tasks.spec.json "open original schema") |
|
||||
|
||||
## default Type
|
||||
|
||||
unknown
|
||||
@@ -1,62 +0,0 @@
|
||||
# Untitled object in Response Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/automation#/properties/automation
|
||||
```
|
||||
|
||||
An array of key value pairs for defining actions and playbooks
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [response_tasks.spec.json*](../../out/response_tasks.spec.json "open original schema") |
|
||||
|
||||
## automation Type
|
||||
|
||||
`object` ([Details](response_tasks-properties-automation.md))
|
||||
|
||||
## automation Constraints
|
||||
|
||||
**minimum number of items**: the minimum number of items for this array is: `1`
|
||||
|
||||
**unique items**: all items in this array must be unique. Duplicates are not allowed.
|
||||
|
||||
## automation Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
{
|
||||
"is_note_required": false,
|
||||
"sla_type": "minutes",
|
||||
"sla": "",
|
||||
"role": "",
|
||||
"action": [],
|
||||
"playbooks": []
|
||||
}
|
||||
```
|
||||
|
||||
## automation Examples
|
||||
|
||||
```yaml
|
||||
is_note_required: false
|
||||
sla_type: minutes
|
||||
sla: 30
|
||||
action:
|
||||
- run_query
|
||||
playbooks:
|
||||
- scm: local
|
||||
playbook: automate something
|
||||
- scm: local
|
||||
playbook: automate something else
|
||||
|
||||
```
|
||||
|
||||
# automation Properties
|
||||
|
||||
| Property | Type | Required | Nullable | Defined by |
|
||||
| :-------------------- | :--- | :------- | :---------- | :--------- |
|
||||
| Additional Properties | Any | Optional | can be null | |
|
||||
|
||||
## Additional Properties
|
||||
|
||||
Additional properties are allowed and do not have to follow a specific schema
|
||||
@@ -1,27 +0,0 @@
|
||||
# Untitled integer in Response Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/sla#/properties/sla
|
||||
```
|
||||
|
||||
Measured integer for Service Level Agreement for completion of the phase
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [response_tasks.spec.json*](../../out/response_tasks.spec.json "open original schema") |
|
||||
|
||||
## sla Type
|
||||
|
||||
`integer`
|
||||
|
||||
## sla Examples
|
||||
|
||||
```yaml
|
||||
5
|
||||
|
||||
```
|
||||
|
||||
```yaml
|
||||
30
|
||||
|
||||
```
|
||||
@@ -1,40 +0,0 @@
|
||||
# Untitled string in Response Schema Schema
|
||||
|
||||
```txt
|
||||
#/properties/sla_type#/properties/sla_type
|
||||
```
|
||||
|
||||
Duration for measured integer for Service Level Agreement for completion of the phase (e.g. minutes, or hours, etc)
|
||||
|
||||
| Abstract | Extensible | Status | Identifiable | Custom Properties | Additional Properties | Access Restrictions | Defined In |
|
||||
| :------------------ | :--------- | :------------- | :---------------------- | :---------------- | :-------------------- | :------------------ | :------------------------------------------------------------------------------------- |
|
||||
| Can be instantiated | No | Unknown status | Unknown identifiability | Forbidden | Allowed | none | [response_tasks.spec.json*](../../out/response_tasks.spec.json "open original schema") |
|
||||
|
||||
## sla_type Type
|
||||
|
||||
`string`
|
||||
|
||||
## sla_type Default Value
|
||||
|
||||
The default value is:
|
||||
|
||||
```json
|
||||
"minutes"
|
||||
```
|
||||
|
||||
## sla_type Examples
|
||||
|
||||
```yaml
|
||||
minutes
|
||||
|
||||
```
|
||||
|
||||
```yaml
|
||||
hours
|
||||
|
||||
```
|
||||
|
||||
```yaml
|
||||
days
|
||||
|
||||
```
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user