-
Notifications
You must be signed in to change notification settings - Fork 120
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
* Update label_request.yml Labeller fails on forks, removing workflow from dev branches. * Sample code: Sample Uploads API * Code sample: Sample Uploads API * Sample config.json file * Documentation updates * Documentation updates * Documentation updates * Documentation updates * Documentation updates * Documentation updates * Documentation updates * Documentation updates * Documentation updates * Documentation updates * Uploading simple example of containing and uncontaining a host via API * Documentation updates * Documentation updates * Documentation updates * Update labeler.yml Added code samples label tagging * Update labeler.yml * Update wordlist.txt * Linting * Update linting.yml * Sample Uploads sample adjustments * Update bandit.yml Co-authored-by: Shane Shellenbarger <[email protected]>
- Loading branch information
Showing
10 changed files
with
262 additions
and
4 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -19,6 +19,7 @@ autogenerated | |
pytest | ||
ipython | ||
dev | ||
config | ||
cov | ||
FalconDebug | ||
Uber | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -3,7 +3,6 @@ on: | |
pull_request: | ||
branches: | ||
- main | ||
- 'ver_*' | ||
|
||
jobs: | ||
triage: | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,51 @@ | ||
![CrowdStrike Falcon](https://raw.githubusercontent.com/CrowdStrike/falconpy/main/docs/asset/cs-logo.png) | ||
|
||
[![Twitter URL](https://img.shields.io/twitter/url?label=Follow%20%40CrowdStrike&style=social&url=https%3A%2F%2Ftwitter.com%2FCrowdStrike)](https://twitter.com/CrowdStrike) | ||
|
||
# FalconPy usage examples | ||
These examples are provided as a quick start for your project. | ||
|
||
+ [Authentication for Examples](#authentication-for-these-examples) | ||
+ [Samples by API service collection](#samples-by-api-service-collection) | ||
- [Detections](#detections) | ||
- [Event Streams](#event-streams) | ||
- [Falcon Discover](#falcon-discover) | ||
- [Hosts](#hosts) | ||
- [Real Time Response](#real-time-response) | ||
- [Sample Uploads](#sample-uploads) | ||
+ [Suggestions](#suggestions) | ||
|
||
## Authentication for these Examples | ||
In order to expedite sample delivery, we will be following a standard pattern for defining and providing credentials to the API. | ||
This is not the only method of providing these values, and not recommended for production deployments as the config.json file is | ||
**not encrypted**. | ||
|
||
In order to test these samples locally in your development environment, rename the file `config_sample.json` to `config.json` and then | ||
update this file to reflect your current development API credentials. | ||
|
||
## Samples by API service collection | ||
These samples are categorized by API service collection. The list below will grow as more samples are planned. | ||
|
||
### Detections | ||
_Coming Soon_ | ||
|
||
### Event Streams | ||
_Coming Soon_ | ||
|
||
### Falcon Discover | ||
_Coming Soon_ | ||
|
||
### Hosts | ||
_Coming Soon_ | ||
|
||
### Real Time Response | ||
+ [Quarantine a host](real_time_response/quarantine_hosts.py) | ||
|
||
### Sample Uploads | ||
+ [Upload, Retrieve and then Delete a file (Service Class)](sample_uploads/sample_uploads_service.py) | ||
+ [Upload, Retrieve and then Delete a file (Uber Class)](sample_uploads/sample_uploads_uber.py) | ||
|
||
## Suggestions | ||
Got a suggestion for an example you'd like to see? Let us know by posting a message to our [discussion board](https://github.com/CrowdStrike/falconpy/discussions). | ||
|
||
Have an example you've developed yourself that you'd like to share? **_Excellent!_** Please review our [contributing guidelines](/CONTRIBUTING.md) and then submit a pull request. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,4 @@ | ||
{ | ||
"falcon_client_id": "API ID GOES HERE", | ||
"falcon_client_secret": "API SECRET GOES HERE" | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,91 @@ | ||
# ____ _ _____ _ ____ | ||
# | _ \ ___ __ _| | |_ _(_)_ __ ___ ___ | _ \ ___ ___ _ __ ___ _ __ ___ ___ | ||
# | |_) / _ \/ _` | | | | | | '_ ` _ \ / _ \ | |_) / _ \/ __| '_ \ / _ \| '_ \/ __|/ _ \ | ||
# | _ < __/ (_| | | | | | | | | | | | __/ | _ < __/\__ \ |_) | (_) | | | \__ \ __/ | ||
# |_| \_\___|\__,_|_| |_| |_|_| |_| |_|\___| |_| \_\___||___/ .__/ \___/|_| |_|___/\___| | ||
# |_| | ||
# | ||
# This example demonstrates how to apply or lift containment on a host using its hostname. | ||
# This solution makes use of Service Class legacy authentication. | ||
# | ||
import json | ||
import argparse | ||
# Import necessary FalconPy classes | ||
from falconpy import oauth2 as FalconAuth | ||
from falconpy import hosts as FalconHosts | ||
|
||
# Setup our argument parser | ||
parser = argparse.ArgumentParser("Script that leverages Falcon API to (un)contain hosts") | ||
parser.add_argument('-c', '--creds_file', dest='creds_file', help='Path to creds json file', required=True) | ||
parser.add_argument('-H', '--hostname', dest='hostname', help='Hostname to quarantine', required=True) | ||
parser.add_argument('-l', '--lift', dest='lift_containment', action="store_true", help='Lift containment', default=False) | ||
# Parse our ingested arguments | ||
args = parser.parse_args() | ||
# Hostname of the machine to contain / release | ||
hostname = args.hostname | ||
# Default action is to quarantine | ||
if args.lift_containment: | ||
action = "lift_containment" | ||
else: | ||
action = "contain" | ||
# Use the credentials file provided | ||
creds_file = args.creds_file | ||
# Load the contents of the creds file into the creds dictionary | ||
with open(creds_file) as f: | ||
creds = json.load(f) | ||
# Create an instance of our OAuth2 authorization class using our ingested creds | ||
authorization = FalconAuth.OAuth2(creds={ | ||
"client_id": creds['falcon_client_id'], | ||
"client_secret": creds['falcon_client_secret'] | ||
}) | ||
# Try to generate a token | ||
try: | ||
token = authorization.token()['body']['access_token'] | ||
except Exception as e: | ||
# Exit out on authentication errors | ||
print("Failed to authenticate") | ||
print(e) | ||
exit(-1) | ||
# If we have a token, proceed to the next step | ||
if token: | ||
# Create an instance of the Hosts class | ||
falcon = FalconHosts.Hosts(access_token=token) | ||
# Create our parameter payload, using our ingested hostname as a filter | ||
PARAMS = { | ||
'offset': 0, | ||
'limit': 10, | ||
'filter': f"hostname:'{hostname}'" | ||
} | ||
# Query the Hosts API for hosts that match our filter pattern | ||
response = falcon.QueryDevicesByFilter(parameters=PARAMS) | ||
# Retrieve the list of IDs returned | ||
contain_ids = response['body']['resources'] | ||
# Output the result | ||
print(json.dumps(response, indent=4)) | ||
|
||
if not contain_ids: | ||
# No hosts were found, exit out | ||
print(f"[-] Could not find hostname: {hostname} - Please verify proper case") | ||
exit(-2) | ||
|
||
# Create our next payload based upon the action requested | ||
PARAMS = { | ||
'action_name': action | ||
} | ||
# Our body payload will contain our list of IDs | ||
BODY = { | ||
'ids': contain_ids | ||
} | ||
# Provide a status update to the terminal | ||
if action == "contain": | ||
print(f"\n[+] Containing: {hostname}\n") | ||
else: | ||
print(f"\n[+] Lifting Containment: {hostname}\n") | ||
|
||
# Perform the requested action | ||
# TODO: Get rid of action_name="contain" once bug is resolved | ||
# BUG: https://github.com/CrowdStrike/falconpy/issues/114 | ||
response = falcon.PerformActionV2(parameters=PARAMS, body=BODY, | ||
action_name="contain") | ||
# Output the result | ||
print(json.dumps(response, indent=4)) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,48 @@ | ||
# ____ _ _ _ _ _ | ||
# / ___| __ _ _ __ ___ _ __ | | ___ | | | |_ __ | | ___ __ _ __| |___ | ||
# \___ \ / _` | '_ ` _ \| '_ \| |/ _ \ | | | | '_ \| |/ _ \ / _` |/ _` / __| | ||
# ___) | (_| | | | | | | |_) | | __/ | |_| | |_) | | (_) | (_| | (_| \__ \ | ||
# |____/ \__,_|_| |_| |_| .__/|_|\___| \___/| .__/|_|\___/ \__,_|\__,_|___/ | ||
# |_| |_| | ||
# | ||
# ____ _ ____ _ | ||
# / ___| ___ _ ____ _(_) ___ ___ / ___| | __ _ ___ ___ | ||
# \___ \ / _ \ '__\ \ / / |/ __/ _ \ | | | |/ _` / __/ __| | ||
# ___) | __/ | \ V /| | (_| __/ | |___| | (_| \__ \__ \ | ||
# |____/ \___|_| \_/ |_|\___\___| \____|_|\__,_|___/___/ | ||
# | ||
# | ||
# These examples show how to interact with the Sample Uploads API using the Service Class | ||
# This example uses Credential authentication and supports token refresh / authentication free usage. | ||
# | ||
import json | ||
# Import the Sample Uploads service class | ||
from falconpy import sample_uploads as FalconUploads | ||
|
||
# #Grab our config parameters | ||
with open('config.json', 'r') as file_config: | ||
config = json.loads(file_config.read()) | ||
|
||
falcon = FalconUploads.Sample_Uploads(creds={ | ||
"client_id": config["falcon_client_id"], | ||
"client_secret": config["falcon_client_secret"] | ||
} | ||
) | ||
|
||
# Define our file | ||
FILENAME = "testfile.jpg" | ||
# Open the file for binary read, this will be our payload | ||
PAYLOAD = open(FILENAME, 'rb').read() | ||
# Upload the file using the Sample Uploads API, name this file "newfile.jpg" in the API | ||
# Since we are using the Service Class, we do not need to specify the content type | ||
response = falcon.UploadSampleV3(file_name="newfile.jpg", file_data=PAYLOAD) | ||
# Grab the SHA256 unique identifier for the file we just uploaded | ||
sha = response["body"]["resources"][0]["sha256"] | ||
# Download a copy of this file, use the SHA256 ID to retrieve it | ||
response = falcon.GetSampleV3(ids=sha) | ||
# Save the result to a new file | ||
open('serviceclass.jpg', 'wb').write(response) | ||
# Delete the file from the API | ||
response = falcon.DeleteSampleV3(ids=sha) | ||
# Print the results of our delete command | ||
print(json.dumps(response, indent=4)) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,47 @@ | ||
# ____ _ _ _ _ _ | ||
# / ___| __ _ _ __ ___ _ __ | | ___ | | | |_ __ | | ___ __ _ __| |___ | ||
# \___ \ / _` | '_ ` _ \| '_ \| |/ _ \ | | | | '_ \| |/ _ \ / _` |/ _` / __| | ||
# ___) | (_| | | | | | | |_) | | __/ | |_| | |_) | | (_) | (_| | (_| \__ \ | ||
# |____/ \__,_|_| |_| |_| .__/|_|\___| \___/| .__/|_|\___/ \__,_|\__,_|___/ | ||
# |_| |_| | ||
# | ||
# | ||
# _ _ _ ____ _ | ||
# | | | | |__ ___ _ __ / ___| | __ _ ___ ___ | ||
# | | | | '_ \ / _ \ '__| | | | |/ _` / __/ __| | ||
# | |_| | |_) | __/ | | |___| | (_| \__ \__ \ | ||
# \___/|_.__/ \___|_| \____|_|\__,_|___/___/ | ||
# | ||
# These examples show how to interact with the Sample Uploads API using the Uber class. | ||
# | ||
import json | ||
# Import the Uber Class | ||
from falconpy import api_complete as FalconSDK | ||
|
||
# Grab our config parameters | ||
with open('../config.json', 'r') as file_config: | ||
config = json.loads(file_config.read()) | ||
|
||
# Create an instance of the Uber class | ||
falcon = FalconSDK.APIHarness(creds={ | ||
"client_id": config["falcon_client_id"], | ||
"client_secret": config["falcon_client_secret"] | ||
} | ||
) | ||
|
||
# Define our file | ||
FILENAME = "testfile.jpg" | ||
# Open the file for binary read, this will be our payload | ||
PAYLOAD = open(FILENAME, 'rb').read() | ||
# Upload the file using the Sample Uploads API, name this file "newfile.jpg" in the API | ||
response = falcon.command('UploadSampleV3', file_name="newfile.jpg", data=PAYLOAD, content_type="application/octet-stream") | ||
# Grab the SHA256 unique identifier for the file we just uploaded | ||
sha = response["body"]["resources"][0]["sha256"] | ||
# Download a copy of this file, use the SHA256 ID to retrieve it | ||
response = falcon.command("GetSampleV3", ids=sha) | ||
# Save the result to a new file | ||
open('uberclass.jpg', 'wb').write(response) | ||
# Delete the file from the API | ||
response = falcon.command("DeleteSampleV3", ids=sha) | ||
# Print the results of our delete command | ||
print(json.dumps(response, indent=4)) |