Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
51 changes: 50 additions & 1 deletion bash/containers/falcon-container-sensor-pull/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,16 @@ Optional Flags:
By default, the image name and tag are appended. Use --copy-omit-image-name
and/or --copy-custom-tag to change that behavior.
-v, --version <SENSOR_VERSION> Specify sensor version to retrieve from the registry

Accepts version strings or channel keywords:
-------------------------------------------
latest Latest sensor version (default)
N-1 Previous major.minor release
N-2 Two major.minor releases back
LTS Latest LTS release
LTS-1 Previous LTS release
7.33 Latest build of version 7.33.x
7.33.0-18606 Specific sensor build
-p, --platform <SENSOR_PLATFORM> Specify sensor platform to retrieve, e.g., x86_64, aarch64
-t, --type <SENSOR_TYPE> Specify which sensor to download (Default: falcon-container)

Expand Down Expand Up @@ -144,7 +154,7 @@ Help Options:
| `-s`, `--client-secret <FALCON_CLIENT_SECRET>` | `$FALCON_CLIENT_SECRET` | `None` (Required) | CrowdStrike API Client Secret |
| `-r`, `--region <FALCON_CLOUD>` | `$FALCON_CLOUD` | `us-1` (Optional) | CrowdStrike Region. <br>\**Auto-discovery is only available for [`us-1, us-2, eu-1`] regions.* |
| `-c`, `--copy <REGISTRY/NAMESPACE>` | `$COPY` | `None` (Optional) | Registry you want to copy the sensor image to. Example: `myregistry.com/mynamespace`. <br> *\*By default, the image name and tag are appended. Use `--copy-omit-image-name` and/or `--copy-custom-tag` to change that behavior.* |
| `-v`, `--version <SENSOR_VERSION>` | `$SENSOR_VERSION` | `None` (Optional) | Specify sensor version to retrieve from the registry |
| `-v`, `--version <SENSOR_VERSION>` | `$SENSOR_VERSION` | `None` (Optional) | Specify sensor version to retrieve from the registry. Accepts version strings (e.g., `7.33`, `7.33.0`) or channel keywords: `latest`, `N-1`, `N-2`, `LTS`, `LTS-1` |
| `-p`, `--platform <SENSOR_PLATFORM>` | `$SENSOR_PLATFORM` | `None` (Optional) | Specify sensor platform to retrieve from the registry |
| `-t`, `--type <SENSOR_TYPE>` | `$SENSOR_TYPE` | `falcon-container` (Optional) | Specify which sensor to download [`falcon-container`, `falcon-sensor`, `falcon-sensor-regional`, `falcon-kac`, `falcon-snapshot`, `falcon-imageanalyzer`, `fcs`, `falcon-jobcontroller`, `falcon-registryassessmentexecutor`] ([see more details below](#sensor-types)) |
| `--runtime` | `$CONTAINER_TOOL` | `docker` (Optional) | Use a different container runtime [docker, podman, skopeo]. **Default is Docker**. |
Expand Down Expand Up @@ -183,6 +193,45 @@ The following sensor types are available to download:
| `falcon-jobcontroller` | The Self Hosted Registry Assessment Jobs Controller |
| `falcon-registryassessmentexecutor` | The Self Hosted Registry Assessment Executor |

### Version Channels

The `-v, --version` flag accepts channel keywords for policy-driven deployments without needing to know exact version numbers:

| Keyword | Description |
| :------- | :---------------------------------- |
| `latest` | Latest sensor version (default) |
| `N-1` | Previous major.minor release |
| `N-2` | Two major.minor releases back |
| `LTS` | Latest LTS release |
| `LTS-1` | Previous LTS release |

Channel keywords are case-insensitive (`n-1`, `N-1`, `lts`, `LTS` all work). N-1/N-2 exclude LTS tags from consideration. No additional API scopes are required — channels are resolved entirely from existing registry tag data.

```shell
# Pull latest (default behavior)
./falcon-container-sensor-pull.sh \
--client-id <FALCON_CLIENT_ID> \
--client-secret <FALCON_CLIENT_SECRET>

# Pull the previous major.minor release (N-1)
./falcon-container-sensor-pull.sh \
--client-id <FALCON_CLIENT_ID> \
--client-secret <FALCON_CLIENT_SECRET> \
--version N-1

# Pull the latest LTS release
./falcon-container-sensor-pull.sh \
--client-id <FALCON_CLIENT_ID> \
--client-secret <FALCON_CLIENT_SECRET> \
--version LTS

# Pull the previous LTS release
./falcon-container-sensor-pull.sh \
--client-id <FALCON_CLIENT_ID> \
--client-secret <FALCON_CLIENT_SECRET> \
--version LTS-1
```

### Examples

#### Example downloading the Falcon Kubernetes Admission Controller
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,17 @@ Optional Flags:
By default, the image name and tag are appended. Use --copy-omit-image-name
and/or --copy-custom-tag to change that behavior.
-v, --version <SENSOR_VERSION> Specify sensor version to retrieve from the registry

Accepts version strings or channel keywords:
-------------------------------------------
latest Latest sensor version (default)
N-1 Previous major.minor release
N-2 Two major.minor releases back
LTS Latest LTS release
LTS-1 Previous LTS release
7.33 Latest build of version 7.33.x
7.33.0-18606 Specific sensor build

-p, --platform <SENSOR_PLATFORM> Specify sensor platform to retrieve, e.g., x86_64, aarch64
-t, --type <SENSOR_TYPE> Specify which sensor to download (Default: falcon-container)

Expand Down Expand Up @@ -454,6 +465,88 @@ display_api_scopes() {
esac
}

# Extract clean tag strings from list_tags JSON output
extract_raw_tags() {
list_tags | awk '
/^[[:space:]]*"[0-9]/ {
gsub(/^[[:space:]]*"/, "")
gsub(/"[[:space:]]*,?[[:space:]]*$/, "")
if (length($0) > 0) print $0
}
'
}

# Resolve version channel keywords (latest, N-1, N-2, LTS, LTS-1) to version prefixes
resolve_version_channel() {
local input="$1"
local normalized all_tags major_minor_versions lts_tags lts_versions target_version

normalized=$(echo "$input" | tr '[:upper:]' '[:lower:]')

case "$normalized" in
latest)
echo ""
return 0
;;
n-1 | n-2 | lts | lts-1)
all_tags=$(extract_raw_tags)
if [ -z "$all_tags" ]; then
die "No tags found for sensor type: ${SENSOR_TYPE}"
fi
;;
*)
# Not a channel keyword — pass through as-is
echo "$input"
return 0
;;
esac

case "$normalized" in
n-1)
major_minor_versions=$(echo "$all_tags" | grep -v "\-LTS" |
awk -F'.' '{ print $1"."$2 }' | sort -u -V)
if [ "$(echo "$major_minor_versions" | wc -l)" -lt 2 ]; then
die "Not enough versions available for N-1. Only $(echo "$major_minor_versions" | wc -l | tr -d ' ') major.minor version(s) found."
fi
target_version=$(echo "$major_minor_versions" | tail -2 | head -1)
;;
n-2)
major_minor_versions=$(echo "$all_tags" | grep -v "\-LTS" |
awk -F'.' '{ print $1"."$2 }' | sort -u -V)
if [ "$(echo "$major_minor_versions" | wc -l)" -lt 3 ]; then
die "Not enough versions available for N-2. Only $(echo "$major_minor_versions" | wc -l | tr -d ' ') major.minor version(s) found."
fi
target_version=$(echo "$major_minor_versions" | tail -3 | head -1)
;;
lts)
lts_tags=$(echo "$all_tags" | grep "\-LTS")
if [ -z "$lts_tags" ]; then
die "No LTS versions found for sensor type: ${SENSOR_TYPE}"
fi
lts_versions=$(echo "$lts_tags" | awk -F'.' '{ print $1"."$2 }' | sort -u -V)
target_version=$(echo "$lts_versions" | tail -1)
;;
lts-1)
lts_tags=$(echo "$all_tags" | grep "\-LTS")
if [ -z "$lts_tags" ]; then
die "No LTS versions found for sensor type: ${SENSOR_TYPE}"
fi
lts_versions=$(echo "$lts_tags" | awk -F'.' '{ print $1"."$2 }' | sort -u -V)
if [ "$(echo "$lts_versions" | wc -l)" -lt 2 ]; then
die "Not enough LTS versions available for LTS-1. Only $(echo "$lts_versions" | wc -l | tr -d ' ') LTS version(s) found."
fi
target_version=$(echo "$lts_versions" | tail -2 | head -1)
;;
esac

if [ -z "$target_version" ]; then
return 1
fi

echo "$target_version"
return 0
}

# Smart version matching function
match_sensor_version() {
local requested_version="$1"
Expand All @@ -462,14 +555,7 @@ match_sensor_version() {
local version_pattern

# Get all available tags by properly parsing JSON output from list_tags
all_tags=$(list_tags | awk '
/^[[:space:]]*"[0-9]/ {
# Extract quoted tag (lines starting with version numbers), remove surrounding quotes and whitespace
gsub(/^[[:space:]]*"/, "")
gsub(/"[[:space:]]*,?[[:space:]]*$/, "")
if (length($0) > 0) print $0
}
')
all_tags=$(extract_raw_tags)

if [ -z "$requested_version" ]; then
# If no version specified, get the latest version
Expand Down Expand Up @@ -835,10 +921,14 @@ if [ "${ERROR}" = "true" ]; then
die "ERROR: ${CONTAINER_TOOL} login failed. Error message: ${error_message}"
fi

#Get latest sensor version
set +e # Temporarily disable exit-on-error for version matching
LATESTSENSOR=$(match_sensor_version "$SENSOR_VERSION")
set -e # Re-enable exit-on-error
# Resolve channel keywords (latest, N-1, N-2, LTS, LTS-1) to version prefixes.
RESOLVED_VERSION=$(resolve_version_channel "$SENSOR_VERSION")

# Get latest sensor version
# match_sensor_version returns 1 for "no match" — a soft failure we handle below.
set +e
LATESTSENSOR=$(match_sensor_version "$RESOLVED_VERSION")
set -e # Re-enable exit-on-error

# Check if version matching was successful
if [ -z "$LATESTSENSOR" ]; then
Expand All @@ -847,6 +937,7 @@ if [ -z "$LATESTSENSOR" ]; then
Available versions can be listed with: $0 --list-tags -t ${SENSOR_TYPE}

Tips for version matching:
- Use channel keywords: -v latest, -v N-1, -v N-2, -v LTS, -v LTS-1
- Use exact version: -v 7.31.0
- Use partial version: -v 7.31 (matches latest 7.31.x)
- Use major version: -v 7 (matches latest 7.x.x)
Expand Down
Loading