Google Cloud Functions
Google Cloud Functions is an event-driven serverless compute platform that enables you to run your code locally or in the cloud without having to provision servers.
Utilities · Google Cloud Functions
Details
| ID | Google Cloud Functions |
|---|---|
| Provider | |
| Category | Utilities |
| From Version | 5.0.0 |
| Docker Image | demisto/google-api-py3:1.0.0.10182333 |
| Supported Modules | Agentix XSIAM |
README
Google Cloud Functions is an event-driven serverless compute platform that enables you to run your code locally or in the cloud without having to provision servers.
This integration was integrated and tested with API version 1 of Google Cloud Functions
Configure Google Cloud Functions in Cortex
| Parameter | Description | Required |
|---|---|---|
| credentials_json | Service account private key file contents (JSON) | True |
| project_id | Default project ID | False |
| region | Default region | False |
| proxy | Use system proxy settings | False |
| insecure | Trust any certificate (not secure) | False |
Commands
You can execute these commands from the CLI, as part of an automation, or in a playbook.
After you successfully execute a command, a DBot message appears in the War Room with the command details.
google-cloud-functions-list
Lists all Google Cloud functions.
Base Command
google-cloud-functions-list
Input
| Argument Name | Description | Required |
|---|---|---|
| project_id | The project ID the Google Cloud function is in. Default is the instance's project. | Optional |
| region | The region of the Google Cloud function. Default is all regions. You can get a full list of regions using the google-cloud-function-regions-list command. |
Optional |
Context Output
| Path | Type | Description |
|---|---|---|
| GoogleCloudFunctions.Function.name | String | A user-defined name of the Google Cloud function. |
| GoogleCloudFunctions.Function.status | String | Status of the Google Cloud function deployment. The status can be: ACTIVE, OFFLINE, DEPLOY_IN_PROGRESS, DELETE_IN_PROGRESS, UNKNOWN. |
| GoogleCloudFunctions.Function.labels | String | Labels associated with this Google Cloud function. |
| GoogleCloudFunctions.Function.runtime | String | The time in which to run the Google Cloud function. |
Command Example
##### Context Example
{
“GoogleCloudFunctions”: {
“Function”: [
{
“availableMemoryMb”: 128,
“entryPoint”: “hello_world”,
“httpsTrigger”: {
“url”: “www.example.com”
},
“ingressSettings”: “ALLOW_ALL”,
“labels”: {
“deployment-tool”: “console-cloud”
},
“name”: “projects/project/locations/us-central1/functions/demisto-func”,
“runtime”: “python37”,
“serviceAccountEmail”: “email”,
“sourceUploadUrl”: “”,
“status”: “ACTIVE”,
“timeout”: “60s”,
“updateTime”: “2020-04-05T12:43:29.610Z”,
“versionId”: “1”
}
]
}
}
##### Human Readable Output
### Functions in project "gcp-integrations" and region "us-central1"
|name|httpsTrigger|status|entryPoint|timeout|availableMemoryMb|serviceAccountEmail|updateTime|versionId|labels|sourceUploadUrl|runtime|ingressSettings|
|---|---|---|---|---|---|---|---|---|---|---|---|---|
| projects/project/locations/us-central1/functions/demisto-func | url: www.example.com | ACTIVE | hello_world | 60s | 128 | email | 2020-04-05T12:43:29.610Z | 1 | deployment-tool: console-cloud | | python37 | ALLOW_ALL |
### google-cloud-function-regions-list
***
Lists all regions in the project.
##### Base Command
`google-cloud-function-regions-list`
##### Input
| **Argument Name** | **Description** | **Required** |
| --- | --- | --- |
| project_id | The project ID the Google Cloud function is in. Default is the instance's project. | Optional |
##### Context Output
| **Path** | **Type** | **Description** |
| --- | --- | --- |
| GoogleCloudFunctions.Region.locationId | String | The location ID of the region. |
| GoogleCloudFunctions.Region.name | String | The full name of the region. |
| GoogleCloudFunctions.Region.labels | String | The labels for the region. |
##### Command Example
```!google-cloud-function-regions-list```
##### Context Example
{
“GoogleCloudFunctions”: {
“Region”: [
{
“labels”: {
“cloud.googleapis.com/region”: “europe-west1”
},
“locationId”: “europe-west1”,
“name”: “projects/gcp-integrations/locations/europe-west1”
},
{
“labels”: {
“cloud.googleapis.com/region”: “europe-west3”
},
“locationId”: “europe-west3”,
“name”: “projects/gcp-integrations/locations/europe-west3”
},
{
“labels”: {
“cloud.googleapis.com/region”: “europe-west2”
},
“locationId”: “europe-west2”,
“name”: “projects/gcp-integrations/locations/europe-west2”
},
{
“labels”: {
“cloud.googleapis.com/region”: “us-central1”
},
“locationId”: “us-central1”,
“name”: “projects/gcp-integrations/locations/us-central1”
},
{
“labels”: {
“cloud.googleapis.com/region”: “us-east1”
},
“locationId”: “us-east1”,
“name”: “projects/gcp-integrations/locations/us-east1”
},
{
“labels”: {
“cloud.googleapis.com/region”: “us-east4”
},
“locationId”: “us-east4”,
“name”: “projects/gcp-integrations/locations/us-east4”
},
{
“labels”: {
“cloud.googleapis.com/region”: “asia-northeast1”
},
“locationId”: “asia-northeast1”,
“name”: “projects/gcp-integrations/locations/asia-northeast1”
},
{
“labels”: {
“cloud.googleapis.com/region”: “asia-east2”
},
“locationId”: “asia-east2”,
“name”: “projects/gcp-integrations/locations/asia-east2”
}
]
}
}
##### Human Readable Output
### Regions in project "gcp-integrations"
|locationId|name|labels|
|---|---|---|
| europe-west1 | projects/gcp-integrations/locations/europe-west1 | cloud.googleapis.com/region: europe-west1 |
| europe-west3 | projects/gcp-integrations/locations/europe-west3 | cloud.googleapis.com/region: europe-west3 |
| europe-west2 | projects/gcp-integrations/locations/europe-west2 | cloud.googleapis.com/region: europe-west2 |
| us-central1 | projects/gcp-integrations/locations/us-central1 | cloud.googleapis.com/region: us-central1 |
| us-east1 | projects/gcp-integrations/locations/us-east1 | cloud.googleapis.com/region: us-east1 |
| us-east4 | projects/gcp-integrations/locations/us-east4 | cloud.googleapis.com/region: us-east4 |
| asia-northeast1 | projects/gcp-integrations/locations/asia-northeast1 | cloud.googleapis.com/region: asia-northeast1 |
| asia-east2 | projects/gcp-integrations/locations/asia-east2 | cloud.googleapis.com/region: asia-east2 |
### google-cloud-function-get-by-name
***
Gets the details of a specific Google Cloud function.
##### Base Command
`google-cloud-function-get-by-name`
##### Input
| **Argument Name** | **Description** | **Required** |
| --- | --- | --- |
| project_id | The project ID the Google Cloud function is in. Default is the instance's project. | Optional |
| region | The region of the Google Cloud function. You can get a full list of regions using the `google-cloud-function-regions-list` command. Default is all regions. | Optional |
| function_name | The name of the function. | Required |
##### Context Output
| **Path** | **Type** | **Description** |
| --- | --- | --- |
| GoogleCloudFunctions.Function.name | String | A user\-defined name of the Google Cloud function. |
| GoogleCloudFunctions.Function.status | String | Status of the Google Cloud function deployment. The status can be ACTIVE, OFFLINE, DEPLOY\_IN\_PROGRESS, DELETE\_IN\_PROGRESS, UNKNOWN. |
| GoogleCloudFunctions.Function.labels | String | The labels associated with this Google Cloud Function. |
| GoogleCloudFunctions.Function.runtime | String | The time in which to run the Google Cloud function. |
##### Command Example
```!google-cloud-function-get-by-name function_name="demisto-func"```
##### Context Example
{
“GoogleCloudFunctions”: {
“Function”: {
“availableMemoryMb”: 128,
“entryPoint”: “hello_world”,
“httpsTrigger”: {
“url”: “”
},
“ingressSettings”: “ALLOW_ALL”,
“labels”: {
“deployment-tool”: “console-cloud”
},
“name”: “projects/project/locations/us-central1/functions/demisto-func”,
“runtime”: “python37”,
“serviceAccountEmail”: “email”,
“sourceUploadUrl”: “”,
“status”: “ACTIVE”,
“timeout”: “60s”,
“updateTime”: “2020-04-05T12:43:29.610Z”,
“versionId”: “1”
}
}
}
##### Human Readable Output
### Here are the details for demisto-func
|name|httpsTrigger|status|entryPoint|timeout|availableMemoryMb|serviceAccountEmail|updateTime|versionId|labels|sourceUploadUrl|runtime|ingressSettings|
|---|---|---|---|---|---|---|---|---|---|---|---|---|
| projects/project/locations/us-central1/functions/demisto-func | url: www.example.com | ACTIVE | hello_world | 60s | 128 | email | 2020-04-05T12:43:29.610Z | 1 | deployment-tool: console-cloud | | python37 | ALLOW_ALL |
### google-cloud-function-execute
***
Executes a Google Cloud function.
##### Base Command
`google-cloud-function-execute`
##### Input
| **Argument Name** | **Description** | **Required** |
| --- | --- | --- |
| function_name | The name of the Google Cloud function to execute. | Required |
| region | The region of the Google Cloud function. Default is all regions. You can get a full list of regions using the `google-cloud-function-regions-list` command. | Optional |
| parameters | The Google Cloud function parameters in a key:value format. Multiple parameters should be comma-separated (i.e., key1:value1,key2:value2). | Optional |
##### Context Output
| **Path** | **Type** | **Description** |
| --- | --- | --- |
| GoogleCloudFunctions.Execution.executionId | String | Execution ID of the Google Cloud function invocated. |
| GoogleCloudFunctions.Execution.result | String | Result populated for successful execution of a synchronous Google Cloud function. It will not be populated if the Google Cloud function does not return a result through context. |
| GoogleCloudFunctions.Execution.error | String | Either a system or user\-function generated error. Set if the execution was not successful. |
##### Command Example
```!google-cloud-function-execute function_name=demisto-func parameters=message:hell\"oThere```
##### Context Example
{
“GoogleCloudFunctions”: {
“Execution”: {
“executionId”: “xp9hifb4y996”,
“result”: “hell"oThere”
}
}
}
```
Human Readable Output
Execution details for demisto-func
| executionId | result |
|---|---|
| xp9hifb4y996 | hell”oThere |
Configuration parameters
credentials_json— Service account private key file contents (JSON)project_id_creds— Default project IDproject_id— Default project IDregion— Default regionproxy— Use system proxy settingsinsecure— Trust any certificate (not secure)
Commands (4)
-
google-cloud-function-executeExecutes a Google Cloud function.
-
google-cloud-function-get-by-nameGets the details of a specific Google Cloud function.
-
google-cloud-function-regions-listLists all regions in the project.
-
google-cloud-functions-listLists all Google Cloud functions.
import demistomock as demisto from CommonServerPython import * # noqa: E402 lgtm [py/polluting-import] from CommonServerUserPython import * # noqa: E402 lgtm [py/polluting-import] """ IMPORTS """ import json import urllib.parse import httplib2 from apiclient import discovery from oauth2client import service_account class GoogleClient: """ A Client class to wrap the google cloud api library. """ def __init__( self, service_name: str, service_version: str, client_secret: str, scopes: list, proxy: bool, insecure: bool, **kwargs ): """ :param service_name: The name of the service. You can find this and the service here https://github.com/googleapis/google-api-python-client/blob/master/docs/dyn/index.md :param service_version:The version of the API. :param client_secret: A string of the credentials.json generated :param scopes: The scope needed for the project. Might be different per function. (i.e. ['https://www.googleapis.com/auth/cloud-platform']) :param proxy: :param insecure: :param kwargs: """ self.project = kwargs.get("project", "") self.region = kwargs.get("region", "-") credentials = service_account.ServiceAccountCredentials.from_json_keyfile_dict(client_secret, scopes=scopes) if proxy or insecure: http_client = credentials.authorize(self.get_http_client_with_proxy(proxy, insecure)) self.service = discovery.build(service_name, service_version, http=http_client) else: self.service = discovery.build(service_name, service_version, credentials=credentials) # disable-secrets-detection-start @staticmethod def get_http_client_with_proxy(proxy, insecure): """ Create an http client with proxy with whom to use when using a proxy. :param proxy: Whether to use a proxy. :param insecure: Whether to disable ssl and use an insecure connection. :return: """ if proxy: proxies = handle_proxy() https_proxy = proxies.get("https") http_proxy = proxies.get("http") proxy_conf = https_proxy if https_proxy else http_proxy # if no proxy_conf - ignore proxy if proxy_conf: if not proxy_conf.startswith("https") and not proxy_conf.startswith("http"): proxy_conf = "https://" + proxy_conf parsed_proxy = urllib.parse.urlparse(proxy_conf) proxy_info = httplib2.ProxyInfo( proxy_type=httplib2.socks.PROXY_TYPE_HTTP, proxy_host=parsed_proxy.hostname, proxy_port=parsed_proxy.port, proxy_user=parsed_proxy.username, proxy_pass=parsed_proxy.password, ) return httplib2.Http(proxy_info=proxy_info, disable_ssl_certificate_validation=insecure) return httplib2.Http(disable_ssl_certificate_validation=insecure) # disable-secrets-detection-end def functions_list(self, region=None, project_id=None): if project_id: self.project = project_id if region: self.region = region parent = f"projects/{self.project}/locations/{self.region}" return self.service.projects().locations().functions().list(parent=parent).execute() def region_list(self, project_id): if project_id: self.project = project_id name = f"projects/{self.project}" return self.service.projects().locations().list(name=name).execute() def function_by_name(self, function_name, region=None, project_id=None): if project_id: self.project = project_id if region: self.region = region name = f"projects/{self.project}/locations/{self.region}/functions/{function_name}" return self.service.projects().locations().functions().get(name=name).execute() def execute_function(self, function_name: str, data: str, region, project_id): if project_id: self.project = project_id if region: self.region = region name = f"projects/{self.project}/locations/{self.region}/functions/{function_name}" body = {"data": data} return self.service.projects().locations().functions().call(name=name, body=body).execute() """COMMAND FUNCTIONS""" def functions_list_command(client: GoogleClient, args: dict): region = client.region project_id = client.project res = client.functions_list(region, project_id) functions = res.get("functions", []) if not functions: return "No functions found.", {}, {} keys = list(functions[0].keys()) keys.remove("name") disp_region = "All" if client.region == "-" else client.region hr = tableToMarkdown(f'Functions in project "{client.project}" and region "{disp_region}"', functions, ["name"] + keys) ec = {"GoogleCloudFunctions.Function(val.name && val.name == obj.name)": functions} return hr, ec, res def region_list_command(client: GoogleClient, args: dict): project_id = args.get("project_id") res = client.region_list(project_id) regions = res.get("locations", []) hr = tableToMarkdown(f'Regions in project "{client.project}"', regions, ["locationId", "name", "labels"]) ec = {"GoogleCloudFunctions.Region(val.locationId && val.locationId == obj.locationId)": regions} return hr, ec, res def get_function_by_name_command(client: GoogleClient, args: dict): function_name = args.get("function_name", "") project_id = args.get("project_id") region = args.get("region") res = client.function_by_name(function_name, region, project_id) keys = list(res.keys()) keys.remove("name") hr = tableToMarkdown(f'Here are the details for {args.get("function_name")}:', res, ["name"] + keys) ec = {"GoogleCloudFunctions.Function(val.name && val.name == obj.name)": res} return hr, ec, res def execute_function_command(client: GoogleClient, args: dict): project_id = args.get("project_id") region = args.get("region") function_name = args.get("function_name", "") parameters = format_parameters(args.get("parameters", "")) res = client.execute_function(function_name, parameters, region, project_id) hr = tableToMarkdown(f'Execution details for {args.get("function_name")}:', res) ec = {"GoogleCloudFunctions.Execution(val.executionId && val.executionId == obj.executionId)": res} return hr, ec, res """HELPER FUNCTIONS""" @logger def format_parameters(parameters: str) -> str: """ Receives a key:value string and retuns a dictionary string ({"key":"value"}). In the process strips trailing and leading spaces. :param parameters: The key-value-list :return: """ if not parameters: return "{}" pairs = [] for item in parameters.split(","): try: key, value = item.split(":") except ValueError: raise ValueError(f"Got unexpected parameters {item}.") pairs.append((key.strip(), value.strip())) return json.dumps(dict(pairs)) def resolve_default_region(region: str): # when region is empty, set it to '-' meaning all regions # note : demisto.params().get('region','-') did not worked on Demisto if not region: # from Google API : If you want to list functions in all locations, use "-" in place of a location return "-" return region def resolve_default_project_id(project: str, credentials_json: dict): if not project: # when project_id is empty, get it from credentials_json no_project_id_in_credentials = "project_id" not in credentials_json if no_project_id_in_credentials: # when not provided project id at all, return error return_error("Service account private key file contents does not have a project id") project = credentials_json["project_id"] return project def main(): params = demisto.params() credentials_json = json.loads(params.get("project_id_creds", {}).get("password") or params.get("credentials_json", {})) project = params.get("project_id_creds", {}).get("identifier") or params.get("project_id") project = resolve_default_project_id(project, credentials_json) region = params.get("region") region = resolve_default_region(region) proxy = params.get("proxy", False) insecure = params.get("insecure", False) scopes = ["https://www.googleapis.com/auth/cloud-platform"] client = GoogleClient("cloudfunctions", "v1", credentials_json, scopes, proxy, insecure, project=project, region=region) commands = { "google-cloud-functions-list": functions_list_command, "google-cloud-function-regions-list": region_list_command, "google-cloud-function-get-by-name": get_function_by_name_command, "google-cloud-function-execute": execute_function_command, } """EXECUTION CODE""" cmd_func = demisto.command() LOG(f"Command being called is {cmd_func}") try: if cmd_func == "test-module": functions_list_command(client, {}) demisto.results("ok") else: hr, outputs, raw = commands[cmd_func](client, demisto.args()) return_outputs(hr, outputs, raw) except Exception as e: return_error(f"Failed to execute {cmd_func} command. Error: {e}") raise if __name__ in ("__main__", "__builtin__", "builtins"): main()