Skip to content

Commit

Permalink
fix: Replace region with endpoint (#1380)
Browse files Browse the repository at this point in the history
* Replace region with endpoint

* Update examples

* Update exporter/chronicleexporter/README.md

Co-authored-by: Brandon Johnson <[email protected]>

---------

Co-authored-by: Brandon Johnson <[email protected]>
  • Loading branch information
Miguel Rodriguez and BinaryFissionGames authored Dec 14, 2023
1 parent c931b99 commit 33d7475
Show file tree
Hide file tree
Showing 7 changed files with 32 additions and 72 deletions.
57 changes: 25 additions & 32 deletions exporter/chronicleexporter/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,58 +14,51 @@ This exporter facilitates the sending of logs to Chronicle, which is a security

1. The exporter uses the configured credentials to authenticate with the Google Cloud services.
2. It marshals logs into the format expected by Chronicle.
3. It sends the logs to the appropriate regional Chronicle endpoint.
3. It sends the logs to the appropriate Chronicle endpoint.

## Configuration

The exporter can be configured using the following fields:

| Field | Type | Default | Required | Description |
| ------------------- | ------ | ------- | -------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `region` | string | | `false` | The region where the data will be sent, it must be one of the predefined regions. if no region is specfied defaults to `https://malachiteingestion-pa.googleapis.com` |
| `creds_file_path` | string | | `true` | The file path to the Google credentials JSON file. |
| `creds` | string | | `true` | The Google credentials JSON. |
| `log_type` | string | | `true` | The type of log that will be sent. |
| `raw_log_field` | string | | `false` | The field name for raw logs. |
| `customer_id` | string | | `false` | The customer ID used for sending logs. |
| `override_log_type` | bool | `true` | `false` | Whether or not to override the `log_type` in the config with `attributes["log_type"]` |
| `namespace` | string | | `false` | User-configured environment namespace to identify the data domain the logs originated from. |

### Regions

Predefined regions include multiple global locations such as `Europe Multi-Region`, `Frankfurt`, `London`, `Singapore`, `Sydney`, `Tel Aviv`, `United States Multi-Region`, and `Zurich`. Each region has a specific endpoint URL.
| Field | Type | Default | Required | Description |
| ------------------- | ------ | ---------------------------------------------- | -------- | ------------------------------------------------------------------------------------------- |
| `endpoint` | string | `https://malachiteingestion-pa.googleapis.com` | `false` | The Endpoint for sending to chronicle. |
| `creds_file_path` | string | | `true` | The file path to the Google credentials JSON file. |
| `creds` | string | | `true` | The Google credentials JSON. |
| `log_type` | string | | `true` | The type of log that will be sent. |
| `raw_log_field` | string | | `false` | The field name for raw logs. |
| `customer_id` | string | | `false` | The customer ID used for sending logs. |
| `override_log_type` | bool | `true` | `false` | Whether or not to override the `log_type` in the config with `attributes["log_type"]` |
| `namespace` | string | | `false` | User-configured environment namespace to identify the data domain the logs originated from. |

### Log Type

If the `attributes["log_type"]` field is present in the log, and maps to a known Chronicle `log_type` the exporter will use the value of that field as the log type. If the `attributes["log_type"]` field is not present, the exporter will use the value of the `log_type` configuration field as the log type.

## Credentials

This exporter requires a Google Cloud service account with access to the Chronicle API. The service account must have access to the following endpoint(s):
This exporter requires a Google Cloud service account with access to the Chronicle API. The service account must have access to the endpoint specfied in the config.
Besides the default endpoint, there are also regional endpoints that can be used [here](https://cloud.google.com/chronicle/docs/reference/ingestion-api#regional_endpoints).

The base endpoint is `https://malachiteingestion-pa.googleapis.com`
For additional information on accessing Chronicle, see the [Chronicle documentation](https://cloud.google.com/chronicle/docs/reference/ingestion-api#getting_api_authentication_credentials).

Alternatively, if a `region` is specified:
## Example Configuration

| Region | Endpoint |
| ---------------------------- | ------------------------------------------------------------------- |
| `Europe Multi-Region` | `https://malachiteingestion-pa-europe.googleapis.com` |
| `Frankfurt` | `https://malachiteingestion-pa-europe-west3.googleapis.com` |
| `London` | `https://malachiteingestion-pa-europe-west2.googleapis.com` |
| `Singapore` | `https://malachiteingestion-pa-asia-southeast1.googleapis.com` |
| `Sydney` | `https://malachiteingestion-pa-australia-southeast1.googleapis.com` |
| `Tel Aviv` | `https://malachiteingestion-pa-europe-west4.googleapis.com` |
| `United States Multi-Region` | `https://malachiteingestion-pa.googleapis.com` |
| `Zurich` | `https://malachiteingestion-pa-europe-west6.googleapis.com` |
### Basic Configuration

For additional information on accessing Chronicle, see the [Chronicle documentation](https://cloud.google.com/chronicle/docs/reference/ingestion-api#getting_api_authentication_credentials).
```yaml
chronicle:
creds_file_path: "/path/to/google/creds.json"
log_type: "ABSOLUTE"
customer_id: "customer-123"
```
## Example Configuration
### Basic Configuration with Regional Endpoint
```yaml
chronicle:
region: "Europe Multi-Region"
endpoint: https://malachiteingestion-pa.googleapis.com
creds_file_path: "/path/to/google/creds.json"
log_type: "threat_detection"
log_type: "ONEPASSWORD"
customer_id: "customer-123"
```
21 changes: 1 addition & 20 deletions exporter/chronicleexporter/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,27 +24,14 @@ import (
"go.uber.org/zap"
)

// Alternative regional endpoints for Chronicle.
// https://cloud.google.com/chronicle/docs/reference/search-api#regional_endpoints
var regions = map[string]string{
"Europe Multi-Region": "https://europe-backstory.googleapis.com",
"Frankfurt": "https://europe-west3-backstory.googleapis.com",
"London": "http://europe-west2-backstory.googleapis.com",
"Singapore": "https://asia-southeast1-backstory.googleapis.com",
"Sydney": "https://australia-southeast1-backstory.googleapis.com",
"Tel Aviv": "https://me-west1-backstory.googleapis.com",
"United States Multi-Region": "https://united-states-backstory.googleapis.com",
"Zurich": "https://europe-west6-backstory.googleapis.com",
}

// Config defines configuration for the Chronicle exporter.
type Config struct {
exporterhelper.TimeoutSettings `mapstructure:",squash"` // squash ensures fields are correctly decoded in embedded struct.
exporterhelper.QueueSettings `mapstructure:"sending_queue"`
exporterhelper.RetrySettings `mapstructure:"retry_on_failure"`

// Endpoint is the URL where Chronicle data will be sent.
Region string `mapstructure:"region"`
Endpoint string `mapstructure:"endpoint"`

// CredsFilePath is the file path to the Google credentials JSON file.
CredsFilePath string `mapstructure:"creds_file_path"`
Expand Down Expand Up @@ -78,12 +65,6 @@ func (cfg *Config) Validate() error {
return errors.New("log_type is required")
}

if cfg.Region != "" {
if _, ok := regions[cfg.Region]; !ok {
return errors.New("region is invalid")
}
}

if cfg.RawLogField != "" {
_, err := expr.NewOTTLLogRecordExpression(cfg.RawLogField, component.TelemetrySettings{
Logger: zap.NewNop(),
Expand Down
17 changes: 2 additions & 15 deletions exporter/chronicleexporter/config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,32 +31,21 @@ func TestConfigValidate(t *testing.T) {
config: &Config{
CredsFilePath: "/path/to/creds_file",
Creds: "creds_example",
Region: "United States Multi-Region",
LogType: "log_type_example",
},
expectedErr: "can only specify creds_file_path or creds",
},
{
desc: "LogType is empty",
config: &Config{
Region: "United States Multi-Region",
Creds: "creds_example",
Creds: "creds_example",
},
expectedErr: "log_type is required",
},
{
desc: "Region is invalid",
config: &Config{
Region: "Invalid Region",
Creds: "creds_example",
LogType: "log_type_example",
},
expectedErr: "region is invalid",
},

{
desc: "Valid config with creds",
config: &Config{
Region: "United States Multi-Region",
Creds: "creds_example",
LogType: "log_type_example",
},
Expand All @@ -65,7 +54,6 @@ func TestConfigValidate(t *testing.T) {
{
desc: "Valid config with creds_file_path",
config: &Config{
Region: "United States Multi-Region",
CredsFilePath: "/path/to/creds_file",
LogType: "log_type_example",
},
Expand All @@ -74,7 +62,6 @@ func TestConfigValidate(t *testing.T) {
{
desc: "Valid config with raw log field",
config: &Config{
Region: "United States Multi-Region",
CredsFilePath: "/path/to/creds_file",
LogType: "log_type_example",
RawLogField: `body["field"]`,
Expand Down
5 changes: 1 addition & 4 deletions exporter/chronicleexporter/exporter.go
Original file line number Diff line number Diff line change
Expand Up @@ -92,10 +92,7 @@ func newExporter(cfg *Config, params exporter.CreateSettings) (*chronicleExporte
// buildEndpoint builds the endpoint to send logs to based on the region. there is a default endpoint `https://malachiteingestion-pa.googleapis.com`
// but there are also regional endpoints that can be used instead. the regional endpoints are listed here: https://cloud.google.com/chronicle/docs/reference/search-api#regional_endpoints
func buildEndpoint(cfg *Config) string {
if cfg.Region != "" && regions[cfg.Region] != "" {
return fmt.Sprintf("%s%s", regions[cfg.Region], apiTarget)
}
return fmt.Sprintf("%s%s", baseEndpoint, apiTarget)
return fmt.Sprintf("%s%s", cfg.Endpoint, apiTarget)
}

func (ce *chronicleExporter) Capabilities() consumer.Capabilities {
Expand Down
2 changes: 1 addition & 1 deletion exporter/chronicleexporter/exporter_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ import (

func TestLogsDataPusher(t *testing.T) {
// Set up configuration, logger, and context
cfg := Config{Region: "United States Multi-Region"}
cfg := Config{}
ctx := context.Background()

testCases := []struct {
Expand Down
1 change: 1 addition & 0 deletions exporter/chronicleexporter/factory.go
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ func createDefaultConfig() component.Config {
QueueSettings: exporterhelper.NewDefaultQueueSettings(),
RetrySettings: exporterhelper.NewDefaultRetrySettings(),
OverrideLogType: true,
Endpoint: baseEndpoint,
}
}

Expand Down
1 change: 1 addition & 0 deletions exporter/chronicleexporter/factory_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ func Test_createDefaultConfig(t *testing.T) {
QueueSettings: exporterhelper.NewDefaultQueueSettings(),
RetrySettings: exporterhelper.NewDefaultRetrySettings(),
OverrideLogType: true,
Endpoint: "https://malachiteingestion-pa.googleapis.com",
}

actual := createDefaultConfig()
Expand Down

0 comments on commit 33d7475

Please sign in to comment.