diff --git a/Logos/Commvault-Logo.svg b/Logos/Commvault-Logo.svg new file mode 100644 index 00000000000..3fa535441a9 --- /dev/null +++ b/Logos/Commvault-Logo.svg @@ -0,0 +1,34 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Solutions/Commvault Security IQ/Analytic Rules/Data_Alert.yaml b/Solutions/Commvault Security IQ/Analytic Rules/Data_Alert.yaml new file mode 100644 index 00000000000..d60c63c3b9a --- /dev/null +++ b/Solutions/Commvault Security IQ/Analytic Rules/Data_Alert.yaml @@ -0,0 +1,31 @@ +id: 1d2c3da7-60ec-40be-9c14-bade6eaf3c49 +name: Data Alert +description: | + 'This query identifies clients or servers whose data has been compromised.' +severity: Medium +status: Available +requiredDataConnectors: [] +queryFrequency: 5m +queryPeriod: 5m +triggerOperator: gt +triggerThreshold: 0 +tactics: + - DefenseEvasion + - Impact + +relevantTechniques: + - T1578 + - T1531 +tags: + - Commvault + - Metallic + - Threat Intelligence + - Ransomware +query: | + SecurityIncident + | where Title has "Cvlt Alert" and Description has "Client" and Description has "Compromised" and Status has "New" + | extend extracted_word = extract("Client\\s(.*?)\\sCompromised", 1, Description) + | project TimeGenerated, Title, Description, Status +entityMappings: null +version: 1.0.0 +kind: Scheduled diff --git a/Solutions/Commvault Security IQ/Analytic Rules/IDP_Alert.yaml b/Solutions/Commvault Security IQ/Analytic Rules/IDP_Alert.yaml new file mode 100644 index 00000000000..9731f6f85ae --- /dev/null +++ b/Solutions/Commvault Security IQ/Analytic Rules/IDP_Alert.yaml @@ -0,0 +1,28 @@ +id: c982bcc1-ef73-485b-80d5-2a637ce4ab2b +name: IDP Alert +description: | + 'This query identifies indications of a potential security breach or unauthorized access to the systems and data of the Identity Provider.' +severity: Medium +status: Available +requiredDataConnectors: [] +queryFrequency: 5m +queryPeriod: 5m +triggerOperator: gt +triggerThreshold: 0 +tactics: + - DefenseEvasion + - Impact +relevantTechniques: + - T1578 + - T1531 +tags: + - Commvault + - Metallic + - Threat Intelligence + - Ransomware +query: | + SecurityIncident + | where Title has "Cvlt Alert" and Description == "IDP Compromised" and Status has "New" +entityMappings: null +version: 1.0.0 +kind: Scheduled diff --git a/Solutions/Commvault Security IQ/Analytic Rules/User_Alert.yaml b/Solutions/Commvault Security IQ/Analytic Rules/User_Alert.yaml new file mode 100644 index 00000000000..0b360719c7a --- /dev/null +++ b/Solutions/Commvault Security IQ/Analytic Rules/User_Alert.yaml @@ -0,0 +1,30 @@ +id: 29e0767c-80ac-4689-9a2e-b25b9fc88fce +name: User Alert +description: | + 'This query identifies users whose user account or credentials have been compromised.' +severity: Medium +status: Available +requiredDataConnectors: [] +queryFrequency: 5m +queryPeriod: 5m +triggerOperator: gt +triggerThreshold: 0 +tactics: + - DefenseEvasion + - Impact +relevantTechniques: + - T1578 + - T1531 +tags: + - Commvault + - Metallic + - Threat Intelligence + - Ransomware +query: | + SecurityIncident + | where Title has "Cvlt Alert" and Description has "User" and Description has "Compromised" and Status has "New" + | extend extracted_word = extract("User\\s(.*?)\\sCompromised", 1, Description) + | project TimeGenerated, Title, Description, Status +entityMappings: null +version: 1.0.0 +kind: Scheduled diff --git a/Solutions/Commvault Security IQ/Data/Solution_Commvault Security IQ.json b/Solutions/Commvault Security IQ/Data/Solution_Commvault Security IQ.json new file mode 100644 index 00000000000..ec10f6d5109 --- /dev/null +++ b/Solutions/Commvault Security IQ/Data/Solution_Commvault Security IQ.json @@ -0,0 +1,19 @@ +{ + "Name": "Commvault Security IQ", + "Author": "svc.cv-securityiq@commvault.com", + "Logo": "", + "Description": "This Microsoft Sentinel integration enables Commvault users to ingest alerts and other data into their Microsoft Sentinel instance. With Analytic Rules, Microsoft Sentinel can automatically create Microsoft Sentinel incidents", + "Analytic Rules": [ + "Analytic Rules/Data_Alert.yaml", + "Analytic Rules/IDP_Alert.yaml", + "Analytic Rules/User_Alert.yaml" + ], + "Playbooks": [ + "Playbooks/CommvaultLogicApp/azuredeploy.json" + ], + "Metadata": "SolutionMetadata.json", + "BasePath": "C:\\GitHub\\Azure-Sentinel\\Solutions\\Commvault Security IQ", + "Version": "3.0.0", + "TemplateSpec": true, + "Is1Pconnector": false +} \ No newline at end of file diff --git a/Solutions/Commvault Security IQ/Package/3.0.0.zip b/Solutions/Commvault Security IQ/Package/3.0.0.zip new file mode 100644 index 00000000000..a05bf905d71 Binary files /dev/null and b/Solutions/Commvault Security IQ/Package/3.0.0.zip differ diff --git a/Solutions/Commvault Security IQ/Package/createUiDefinition.json b/Solutions/Commvault Security IQ/Package/createUiDefinition.json new file mode 100644 index 00000000000..b535b6301ee --- /dev/null +++ b/Solutions/Commvault Security IQ/Package/createUiDefinition.json @@ -0,0 +1,159 @@ +{ + "$schema": "https://schema.management.azure.com/schemas/0.1.2-preview/CreateUIDefinition.MultiVm.json#", + "handler": "Microsoft.Azure.CreateUIDef", + "version": "0.1.2-preview", + "parameters": { + "config": { + "isWizard": false, + "basics": { + "description": "\n\n**Note:** _There may be [known issues](https://aka.ms/sentinelsolutionsknownissues) pertaining to this Solution, please refer to them before installing._\n\nThis Microsoft Sentinel integration enables Commvault users to ingest alerts and other data into their Microsoft Sentinel instance. With Analytic Rules, Microsoft Sentinel can automatically create Microsoft Sentinel incidents\n\n**Analytic Rules:** 3, **Playbooks:** 1\n\n[Learn more about Microsoft Sentinel](https://aka.ms/azuresentinel) | [Learn more about Solutions](https://aka.ms/azuresentinelsolutionsdoc)", + "subscription": { + "resourceProviders": [ + "Microsoft.OperationsManagement/solutions", + "Microsoft.OperationalInsights/workspaces/providers/alertRules", + "Microsoft.Insights/workbooks", + "Microsoft.Logic/workflows" + ] + }, + "location": { + "metadata": { + "hidden": "Hiding location, we get it from the log analytics workspace" + }, + "visible": false + }, + "resourceGroup": { + "allowExisting": true + } + } + }, + "basics": [ + { + "name": "getLAWorkspace", + "type": "Microsoft.Solutions.ArmApiControl", + "toolTip": "This filters by workspaces that exist in the Resource Group selected", + "condition": "[greater(length(resourceGroup().name),0)]", + "request": { + "method": "GET", + "path": "[concat(subscription().id,'/providers/Microsoft.OperationalInsights/workspaces?api-version=2020-08-01')]" + } + }, + { + "name": "workspace", + "type": "Microsoft.Common.DropDown", + "label": "Workspace", + "placeholder": "Select a workspace", + "toolTip": "This dropdown will list only workspace that exists in the Resource Group selected", + "constraints": { + "allowedValues": "[map(filter(basics('getLAWorkspace').value, (filter) => contains(toLower(filter.id), toLower(resourceGroup().name))), (item) => parse(concat('{\"label\":\"', item.name, '\",\"value\":\"', item.name, '\"}')))]", + "required": true + }, + "visible": true + } + ], + "steps": [ + { + "name": "analytics", + "label": "Analytics", + "subLabel": { + "preValidation": "Configure the analytics", + "postValidation": "Done" + }, + "bladeTitle": "Analytics", + "elements": [ + { + "name": "analytics-text", + "type": "Microsoft.Common.TextBlock", + "options": { + "text": "This solution installs the following analytic rule templates. After installing the solution, create and enable analytic rules in Manage solution view." + } + }, + { + "name": "analytics-link", + "type": "Microsoft.Common.TextBlock", + "options": { + "link": { + "label": "Learn more", + "uri": "https://docs.microsoft.com/azure/sentinel/tutorial-detect-threats-custom?WT.mc_id=Portal-Microsoft_Azure_CreateUIDef" + } + } + }, + { + "name": "analytic1", + "type": "Microsoft.Common.Section", + "label": "Data Alert", + "elements": [ + { + "name": "analytic1-text", + "type": "Microsoft.Common.TextBlock", + "options": { + "text": "This query identifies clients or servers whose data has been compromised." + } + } + ] + }, + { + "name": "analytic2", + "type": "Microsoft.Common.Section", + "label": "IDP Alert", + "elements": [ + { + "name": "analytic2-text", + "type": "Microsoft.Common.TextBlock", + "options": { + "text": "This query identifies indications of a potential security breach or unauthorized access to the systems and data of the Identity Provider." + } + } + ] + }, + { + "name": "analytic3", + "type": "Microsoft.Common.Section", + "label": "User Alert", + "elements": [ + { + "name": "analytic3-text", + "type": "Microsoft.Common.TextBlock", + "options": { + "text": "This query identifies users whose user account or credentials have been compromised." + } + } + ] + } + ] + }, + { + "name": "playbooks", + "label": "Playbooks", + "subLabel": { + "preValidation": "Configure the playbooks", + "postValidation": "Done" + }, + "bladeTitle": "Playbooks", + "elements": [ + { + "name": "playbooks-text", + "type": "Microsoft.Common.TextBlock", + "options": { + "text": "This solution installs the Playbook templates to help implement your Security Orchestration, Automation and Response (SOAR) operations. After installing the solution, these will be deployed under Playbook Templates in the Automation blade in Microsoft Sentinel. They can be configured and managed from the Manage solution view in Content Hub." + } + }, + { + "name": "playbooks-link", + "type": "Microsoft.Common.TextBlock", + "options": { + "link": { + "label": "Learn more", + "uri": "https://docs.microsoft.com/azure/sentinel/tutorial-respond-threats-playbook?WT.mc_id=Portal-Microsoft_Azure_CreateUIDef" + } + } + } + ] + } + ], + "outputs": { + "workspace-location": "[first(map(filter(basics('getLAWorkspace').value, (filter) => and(contains(toLower(filter.id), toLower(resourceGroup().name)),equals(filter.name,basics('workspace')))), (item) => item.location))]", + "location": "[location()]", + "workspace": "[basics('workspace')]" + } + } +} diff --git a/Solutions/Commvault Security IQ/Package/mainTemplate.json b/Solutions/Commvault Security IQ/Package/mainTemplate.json new file mode 100644 index 00000000000..853fd63499b --- /dev/null +++ b/Solutions/Commvault Security IQ/Package/mainTemplate.json @@ -0,0 +1,874 @@ +{ + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "metadata": { + "author": "svc.cv-securityiq@commvault.com", + "comments": "Solution template for Commvault Security IQ" + }, + "parameters": { + "location": { + "type": "string", + "minLength": 1, + "defaultValue": "[resourceGroup().location]", + "metadata": { + "description": "Not used, but needed to pass arm-ttk test `Location-Should-Not-Be-Hardcoded`. We instead use the `workspace-location` which is derived from the LA workspace" + } + }, + "workspace-location": { + "type": "string", + "defaultValue": "", + "metadata": { + "description": "[concat('Region to deploy solution resources -- separate from location selection',parameters('location'))]" + } + }, + "workspace": { + "defaultValue": "", + "type": "string", + "metadata": { + "description": "Workspace name for Log Analytics where Microsoft Sentinel is setup" + } + } + }, + "variables": { + "_solutionName": "Commvault Security IQ", + "_solutionVersion": "3.0.0", + "solutionId": "commvaultsecurityiq.azure-sentinel-solution-commvaultsecurityiq", + "_solutionId": "[variables('solutionId')]", + "analyticRuleVersion1": "1.0.0", + "analyticRulecontentId1": "1d2c3da7-60ec-40be-9c14-bade6eaf3c49", + "_analyticRulecontentId1": "[variables('analyticRulecontentId1')]", + "TemplateEmptyArray": "[json('[]')]", + "analyticRuleId1": "[resourceId('Microsoft.SecurityInsights/AlertRuleTemplates', variables('analyticRulecontentId1'))]", + "analyticRuleTemplateSpecName1": "[concat(parameters('workspace'),'/Microsoft.SecurityInsights/',concat(parameters('workspace'),'-ar-',uniquestring(variables('_analyticRulecontentId1'))))]", + "_analyticRulecontentProductId1": "[concat(take(variables('_solutionId'),50),'-','ar','-', uniqueString(concat(variables('_solutionId'),'-','AnalyticsRule','-',variables('_analyticRulecontentId1'),'-', variables('analyticRuleVersion1'))))]", + "analyticRuleVersion2": "1.0.0", + "analyticRulecontentId2": "c982bcc1-ef73-485b-80d5-2a637ce4ab2b", + "_analyticRulecontentId2": "[variables('analyticRulecontentId2')]", + "analyticRuleId2": "[resourceId('Microsoft.SecurityInsights/AlertRuleTemplates', variables('analyticRulecontentId2'))]", + "analyticRuleTemplateSpecName2": "[concat(parameters('workspace'),'/Microsoft.SecurityInsights/',concat(parameters('workspace'),'-ar-',uniquestring(variables('_analyticRulecontentId2'))))]", + "_analyticRulecontentProductId2": "[concat(take(variables('_solutionId'),50),'-','ar','-', uniqueString(concat(variables('_solutionId'),'-','AnalyticsRule','-',variables('_analyticRulecontentId2'),'-', variables('analyticRuleVersion2'))))]", + "analyticRuleVersion3": "1.0.0", + "analyticRulecontentId3": "29e0767c-80ac-4689-9a2e-b25b9fc88fce", + "_analyticRulecontentId3": "[variables('analyticRulecontentId3')]", + "analyticRuleId3": "[resourceId('Microsoft.SecurityInsights/AlertRuleTemplates', variables('analyticRulecontentId3'))]", + "analyticRuleTemplateSpecName3": "[concat(parameters('workspace'),'/Microsoft.SecurityInsights/',concat(parameters('workspace'),'-ar-',uniquestring(variables('_analyticRulecontentId3'))))]", + "_analyticRulecontentProductId3": "[concat(take(variables('_solutionId'),50),'-','ar','-', uniqueString(concat(variables('_solutionId'),'-','AnalyticsRule','-',variables('_analyticRulecontentId3'),'-', variables('analyticRuleVersion3'))))]", + "CommvaultLogicApp": "CommvaultLogicApp", + "_CommvaultLogicApp": "[variables('CommvaultLogicApp')]", + "playbookVersion1": "1.0", + "playbookContentId1": "CommvaultLogicApp", + "_playbookContentId1": "[variables('playbookContentId1')]", + "playbookId1": "[resourceId('Microsoft.Logic/workflows', variables('playbookContentId1'))]", + "playbookTemplateSpecName1": "[concat(parameters('workspace'),'/Microsoft.SecurityInsights/',concat(parameters('workspace'),'-pl-',uniquestring(variables('_playbookContentId1'))))]", + "workspaceResourceId": "[resourceId('microsoft.OperationalInsights/Workspaces', parameters('workspace'))]", + "_playbookcontentProductId1": "[concat(take(variables('_solutionId'),50),'-','pl','-', uniqueString(concat(variables('_solutionId'),'-','Playbook','-',variables('_playbookContentId1'),'-', variables('playbookVersion1'))))]", + "blanks": "[replace('b', 'b', '')]", + "_solutioncontentProductId": "[concat(take(variables('_solutionId'),50),'-','sl','-', uniqueString(concat(variables('_solutionId'),'-','Solution','-',variables('_solutionId'),'-', variables('_solutionVersion'))))]" + }, + "resources": [ + { + "type": "Microsoft.OperationalInsights/workspaces/providers/contentTemplates", + "apiVersion": "2023-04-01-preview", + "name": "[variables('analyticRuleTemplateSpecName1')]", + "location": "[parameters('workspace-location')]", + "dependsOn": [ + "[extensionResourceId(resourceId('Microsoft.OperationalInsights/workspaces', parameters('workspace')), 'Microsoft.SecurityInsights/contentPackages', variables('_solutionId'))]" + ], + "properties": { + "description": "Data_Alert_AnalyticalRules Analytics Rule with template version 3.0.0", + "mainTemplate": { + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "[variables('analyticRuleVersion1')]", + "parameters": {}, + "variables": {}, + "resources": [ + { + "type": "Microsoft.SecurityInsights/AlertRuleTemplates", + "name": "[variables('analyticRulecontentId1')]", + "apiVersion": "2022-04-01-preview", + "kind": "Scheduled", + "location": "[parameters('workspace-location')]", + "properties": { + "description": "This query identifies clients or servers whose data has been compromised.", + "displayName": "Data Alert", + "enabled": false, + "query": "SecurityIncident\n| where Title has \"Cvlt Alert\" and Description has \"Client\" and Description has \"Compromised\" and Status has \"New\"\n| extend extracted_word = extract(\"Client\\\\s(.*?)\\\\sCompromised\", 1, Description)\n| project TimeGenerated, Title, Description, Status\n", + "queryFrequency": "PT5M", + "queryPeriod": "PT5M", + "severity": "Medium", + "suppressionDuration": "PT1H", + "suppressionEnabled": false, + "triggerOperator": "GreaterThan", + "triggerThreshold": 0, + "status": "Available", + "requiredDataConnectors": "[variables('TemplateEmptyArray')]", + "tactics": [ + "DefenseEvasion", + "Impact" + ], + "techniques": [ + "T1578", + "T1531" + ] + } + }, + { + "type": "Microsoft.OperationalInsights/workspaces/providers/metadata", + "apiVersion": "2022-01-01-preview", + "name": "[concat(parameters('workspace'),'/Microsoft.SecurityInsights/',concat('AnalyticsRule-', last(split(variables('analyticRuleId1'),'/'))))]", + "properties": { + "description": "Commvault Security IQ Analytics Rule 1", + "parentId": "[variables('analyticRuleId1')]", + "contentId": "[variables('_analyticRulecontentId1')]", + "kind": "AnalyticsRule", + "version": "[variables('analyticRuleVersion1')]", + "source": { + "kind": "Solution", + "name": "Commvault Security IQ", + "sourceId": "[variables('_solutionId')]" + }, + "author": { + "name": "svc.cv-securityiq@commvault.com" + }, + "support": { + "tier": "Partner", + "name": "Commvault", + "email": "support@commvault.com", + "link": "https://www.commvault.com/support" + } + } + } + ] + }, + "packageKind": "Solution", + "packageVersion": "[variables('_solutionVersion')]", + "packageName": "[variables('_solutionName')]", + "packageId": "[variables('_solutionId')]", + "contentSchemaVersion": "3.0.0", + "contentId": "[variables('_analyticRulecontentId1')]", + "contentKind": "AnalyticsRule", + "displayName": "Data Alert", + "contentProductId": "[variables('_analyticRulecontentProductId1')]", + "id": "[variables('_analyticRulecontentProductId1')]", + "version": "[variables('analyticRuleVersion1')]" + } + }, + { + "type": "Microsoft.OperationalInsights/workspaces/providers/contentTemplates", + "apiVersion": "2023-04-01-preview", + "name": "[variables('analyticRuleTemplateSpecName2')]", + "location": "[parameters('workspace-location')]", + "dependsOn": [ + "[extensionResourceId(resourceId('Microsoft.OperationalInsights/workspaces', parameters('workspace')), 'Microsoft.SecurityInsights/contentPackages', variables('_solutionId'))]" + ], + "properties": { + "description": "IDP_Alert_AnalyticalRules Analytics Rule with template version 3.0.0", + "mainTemplate": { + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "[variables('analyticRuleVersion2')]", + "parameters": {}, + "variables": {}, + "resources": [ + { + "type": "Microsoft.SecurityInsights/AlertRuleTemplates", + "name": "[variables('analyticRulecontentId2')]", + "apiVersion": "2022-04-01-preview", + "kind": "Scheduled", + "location": "[parameters('workspace-location')]", + "properties": { + "description": "This query identifies indications of a potential security breach or unauthorized access to the systems and data of the Identity Provider.", + "displayName": "IDP Alert", + "enabled": false, + "query": "SecurityIncident\n| where Title has \"Cvlt Alert\" and Description == \"IDP Compromised\" and Status has \"New\"\n", + "queryFrequency": "PT5M", + "queryPeriod": "PT5M", + "severity": "Medium", + "suppressionDuration": "PT1H", + "suppressionEnabled": false, + "triggerOperator": "GreaterThan", + "triggerThreshold": 0, + "status": "Available", + "requiredDataConnectors": "[variables('TemplateEmptyArray')]", + "tactics": [ + "DefenseEvasion", + "Impact" + ], + "techniques": [ + "T1578", + "T1531" + ] + } + }, + { + "type": "Microsoft.OperationalInsights/workspaces/providers/metadata", + "apiVersion": "2022-01-01-preview", + "name": "[concat(parameters('workspace'),'/Microsoft.SecurityInsights/',concat('AnalyticsRule-', last(split(variables('analyticRuleId2'),'/'))))]", + "properties": { + "description": "Commvault Security IQ Analytics Rule 2", + "parentId": "[variables('analyticRuleId2')]", + "contentId": "[variables('_analyticRulecontentId2')]", + "kind": "AnalyticsRule", + "version": "[variables('analyticRuleVersion2')]", + "source": { + "kind": "Solution", + "name": "Commvault Security IQ", + "sourceId": "[variables('_solutionId')]" + }, + "author": { + "name": "svc.cv-securityiq@commvault.com" + }, + "support": { + "tier": "Partner", + "name": "Commvault", + "email": "support@commvault.com", + "link": "https://www.commvault.com/support" + } + } + } + ] + }, + "packageKind": "Solution", + "packageVersion": "[variables('_solutionVersion')]", + "packageName": "[variables('_solutionName')]", + "packageId": "[variables('_solutionId')]", + "contentSchemaVersion": "3.0.0", + "contentId": "[variables('_analyticRulecontentId2')]", + "contentKind": "AnalyticsRule", + "displayName": "IDP Alert", + "contentProductId": "[variables('_analyticRulecontentProductId2')]", + "id": "[variables('_analyticRulecontentProductId2')]", + "version": "[variables('analyticRuleVersion2')]" + } + }, + { + "type": "Microsoft.OperationalInsights/workspaces/providers/contentTemplates", + "apiVersion": "2023-04-01-preview", + "name": "[variables('analyticRuleTemplateSpecName3')]", + "location": "[parameters('workspace-location')]", + "dependsOn": [ + "[extensionResourceId(resourceId('Microsoft.OperationalInsights/workspaces', parameters('workspace')), 'Microsoft.SecurityInsights/contentPackages', variables('_solutionId'))]" + ], + "properties": { + "description": "User_Alert_AnalyticalRules Analytics Rule with template version 3.0.0", + "mainTemplate": { + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "[variables('analyticRuleVersion3')]", + "parameters": {}, + "variables": {}, + "resources": [ + { + "type": "Microsoft.SecurityInsights/AlertRuleTemplates", + "name": "[variables('analyticRulecontentId3')]", + "apiVersion": "2022-04-01-preview", + "kind": "Scheduled", + "location": "[parameters('workspace-location')]", + "properties": { + "description": "This query identifies users whose user account or credentials have been compromised.", + "displayName": "User Alert", + "enabled": false, + "query": "SecurityIncident\n| where Title has \"Cvlt Alert\" and Description has \"User\" and Description has \"Compromised\" and Status has \"New\"\n| extend extracted_word = extract(\"User\\\\s(.*?)\\\\sCompromised\", 1, Description)\n| project TimeGenerated, Title, Description, Status\n", + "queryFrequency": "PT5M", + "queryPeriod": "PT5M", + "severity": "Medium", + "suppressionDuration": "PT1H", + "suppressionEnabled": false, + "triggerOperator": "GreaterThan", + "triggerThreshold": 0, + "status": "Available", + "requiredDataConnectors": "[variables('TemplateEmptyArray')]", + "tactics": [ + "DefenseEvasion", + "Impact" + ], + "techniques": [ + "T1578", + "T1531" + ] + } + }, + { + "type": "Microsoft.OperationalInsights/workspaces/providers/metadata", + "apiVersion": "2022-01-01-preview", + "name": "[concat(parameters('workspace'),'/Microsoft.SecurityInsights/',concat('AnalyticsRule-', last(split(variables('analyticRuleId3'),'/'))))]", + "properties": { + "description": "Commvault Security IQ Analytics Rule 3", + "parentId": "[variables('analyticRuleId3')]", + "contentId": "[variables('_analyticRulecontentId3')]", + "kind": "AnalyticsRule", + "version": "[variables('analyticRuleVersion3')]", + "source": { + "kind": "Solution", + "name": "Commvault Security IQ", + "sourceId": "[variables('_solutionId')]" + }, + "author": { + "name": "svc.cv-securityiq@commvault.com" + }, + "support": { + "tier": "Partner", + "name": "Commvault", + "email": "support@commvault.com", + "link": "https://www.commvault.com/support" + } + } + } + ] + }, + "packageKind": "Solution", + "packageVersion": "[variables('_solutionVersion')]", + "packageName": "[variables('_solutionName')]", + "packageId": "[variables('_solutionId')]", + "contentSchemaVersion": "3.0.0", + "contentId": "[variables('_analyticRulecontentId3')]", + "contentKind": "AnalyticsRule", + "displayName": "User Alert", + "contentProductId": "[variables('_analyticRulecontentProductId3')]", + "id": "[variables('_analyticRulecontentProductId3')]", + "version": "[variables('analyticRuleVersion3')]" + } + }, + { + "type": "Microsoft.OperationalInsights/workspaces/providers/contentTemplates", + "apiVersion": "2023-04-01-preview", + "name": "[variables('playbookTemplateSpecName1')]", + "location": "[parameters('workspace-location')]", + "dependsOn": [ + "[extensionResourceId(resourceId('Microsoft.OperationalInsights/workspaces', parameters('workspace')), 'Microsoft.SecurityInsights/contentPackages', variables('_solutionId'))]" + ], + "properties": { + "description": "Commvault-Logic-App10 Playbook with template version 3.0.0", + "mainTemplate": { + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "[variables('playbookVersion1')]", + "parameters": { + "PlaybookName": { + "defaultValue": "Commvault-Logic-App10", + "type": "string" + }, + "Automation-Account": { + "defaultValue": "Commvault-Automation-Account", + "type": "string" + }, + "keyvaultName": { + "type": "string" + } + }, + "variables": { + "location": "[parameters('workspace-location')]", + "subscriptionId": "[[subscription().subscriptionId]", + "tenantId": "[[subscription().tenantId]", + "keyvaultApiId": "[[concat('/subscriptions/', variables('subscriptionId'), '/providers/Microsoft.Web/locations/', variables('location'),'/managedApis/keyvault')]", + "AzureautomationConnectionName": "[[concat('Azureautomation-', parameters('PlaybookName'))]", + "MicrosoftSentinelConnectionName": "[[concat('MicrosoftSentinel-', parameters('PlaybookName'))]", + "KeyvaultConnectionName": "[[concat('Keyvault-', parameters('PlaybookName'))]", + "connection-2": "[[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', variables('workspace-location-inline'), '/managedApis/Azureautomation')]", + "_connection-2": "[[variables('connection-2')]", + "connection-3": "[[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', variables('workspace-location-inline'), '/managedApis/Azuresentinel')]", + "_connection-3": "[[variables('connection-3')]", + "connection-4": "[[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', variables('workspace-location-inline'), '/managedApis/Keyvault')]", + "_connection-4": "[[variables('connection-4')]", + "workspace-location-inline": "[concat('[resourceGroup().locatio', 'n]')]", + "workspace-name": "[parameters('workspace')]", + "workspaceResourceId": "[[resourceId('microsoft.OperationalInsights/Workspaces', variables('workspace-name'))]" + }, + "resources": [ + { + "properties": { + "provisioningState": "Succeeded", + "state": "Enabled", + "definition": { + "$schema": "https://schema.management.azure.com/providers/Microsoft.Logic/schemas/2016-06-01/workflowdefinition.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "$connections": { + "type": "Object" + } + }, + "triggers": { + "Microsoft_Sentinel_incident": { + "type": "ApiConnectionWebhook", + "inputs": { + "body": { + "callback_url": "@{listCallbackUrl()}" + }, + "host": { + "connection": { + "name": "@parameters('$connections')['azuresentinel']['connectionId']" + } + }, + "path": "/incident-creation" + } + } + }, + "actions": { + "Access_Token": { + "type": "ApiConnection", + "inputs": { + "host": { + "connection": { + "name": "@parameters('$connections')['keyvault']['connectionId']" + } + }, + "method": "get", + "path": "/secrets/@{encodeURIComponent('access-token')}/value" + } + }, + "Disable_Data_Aging": { + "actions": { + "Disable_Data_Aging_Job": { + "type": "ApiConnection", + "inputs": { + "body": { + "properties": { + "parameters": { + "ClientName": "@triggerBody()?['object']?['properties']?['description']", + "EnvironmentEndpointURL": "@body('Environment_Endpoint_URL')?['value']", + "apiAccessToken": "@body('Access_Token')?['value']" + } + } + }, + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "put", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs", + "queries": { + "runbookName": "Commvault_Disable_Data_Aging", + "wait": true, + "x-ms-api-version": "2015-10-31" + } + } + }, + "Disable_Data_Aging_Job_Output": { + "runAfter": { + "Disable_Data_Aging_Job": [ + "Succeeded" + ] + }, + "type": "ApiConnection", + "inputs": { + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "get", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs/@{encodeURIComponent(body('Disable_Data_Aging_Job')?['properties']?['jobId'])}/output", + "queries": { + "x-ms-api-version": "2015-10-31" + } + } + } + }, + "runAfter": { + "Environment_Endpoint_URL": [ + "Succeeded" + ] + }, + "expression": { + "and": [ + { + "startsWith": [ + "@triggerBody()?['object']?['properties']?['description']", + "Data" + ] + } + ] + }, + "type": "If" + }, + "Disable_IDP": { + "actions": { + "Disable_IDP_Job": { + "type": "ApiConnection", + "inputs": { + "body": { + "properties": { + "parameters": { + "EnvironmentEndpointURL": "@body('Environment_Endpoint_URL')?['value']", + "apiAccessToken": "@body('Access_Token')?['value']" + } + } + }, + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "put", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs", + "queries": { + "runbookName": "Commvault_Disable_IDP", + "wait": true, + "x-ms-api-version": "2015-10-31" + } + } + }, + "Disable_IDP_Job_Output": { + "runAfter": { + "Disable_IDP_Job": [ + "Succeeded" + ] + }, + "type": "ApiConnection", + "inputs": { + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "get", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs/@{encodeURIComponent(body('Disable_IDP_Job')?['properties']?['jobId'])}/output", + "queries": { + "x-ms-api-version": "2015-10-31" + } + } + } + }, + "runAfter": { + "Environment_Endpoint_URL": [ + "Succeeded" + ] + }, + "expression": { + "and": [ + { + "startsWith": [ + "@triggerBody()?['object']?['properties']?['description']", + "IDP" + ] + } + ] + }, + "type": "If" + }, + "Disable_User": { + "actions": { + "Disable_User_Job": { + "type": "ApiConnection", + "inputs": { + "body": { + "properties": { + "parameters": { + "EnvironmentEndpointURL": "@body('Environment_Endpoint_URL')?['value']", + "UserIdentity": "@triggerBody()?['object']?['properties']?['description']", + "apiAccessToken": "@body('Access_Token')?['value']" + } + } + }, + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "put", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs", + "queries": { + "runbookName": "Commvault_Disable_User", + "wait": true, + "x-ms-api-version": "2015-10-31" + } + } + }, + "Disable_User_Job_Output": { + "runAfter": { + "Disable_User_Job": [ + "Succeeded" + ] + }, + "type": "ApiConnection", + "inputs": { + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "get", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs/@{encodeURIComponent(body('Disable_User_Job')?['properties']?['jobId'])}/output", + "queries": { + "x-ms-api-version": "2015-10-31" + } + } + } + }, + "runAfter": { + "Environment_Endpoint_URL": [ + "Succeeded" + ] + }, + "expression": { + "and": [ + { + "startsWith": [ + "@triggerBody()?['object']?['properties']?['description']", + "User" + ] + } + ] + }, + "type": "If" + }, + "Environment_Endpoint_URL": { + "runAfter": { + "Access_Token": [ + "Succeeded" + ] + }, + "type": "ApiConnection", + "inputs": { + "host": { + "connection": { + "name": "@parameters('$connections')['keyvault']['connectionId']" + } + }, + "method": "get", + "path": "/secrets/@{encodeURIComponent('environment-endpoint-url')}/value" + } + } + } + }, + "parameters": { + "$connections": { + "value": { + "azureautomation": { + "connectionId": "[[resourceId('Microsoft.Web/connections', variables('AzureautomationConnectionName'))]", + "connectionName": "[[variables('AzureautomationConnectionName')]", + "id": "[[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', variables('workspace-location-inline'), '/managedApis/Azureautomation')]", + "connectionProperties": { + "authentication": { + "type": "ManagedServiceIdentity" + } + } + }, + "azuresentinel": { + "connectionId": "[[resourceId('Microsoft.Web/connections', variables('MicrosoftSentinelConnectionName'))]", + "connectionName": "[[variables('MicrosoftSentinelConnectionName')]", + "id": "[[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', variables('workspace-location-inline'), '/managedApis/Azuresentinel')]", + "connectionProperties": { + "authentication": { + "type": "ManagedServiceIdentity" + } + } + }, + "keyvault": { + "connectionId": "[[resourceId('Microsoft.Web/connections', variables('KeyvaultConnectionName'))]", + "connectionName": "[[variables('KeyvaultConnectionName')]", + "id": "[[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', variables('workspace-location-inline'), '/managedApis/Keyvault')]", + "connectionProperties": { + "authentication": { + "type": "ManagedServiceIdentity" + } + } + } + } + } + } + }, + "name": "[[parameters('PlaybookName')]", + "type": "Microsoft.Logic/workflows", + "location": "[[variables('workspace-location-inline')]", + "tags": { + "hidden-SentinelTemplateName": "Commvault-Logic-App1", + "hidden-SentinelTemplateVersion": "1.0", + "hidden-SentinelWorkspaceId": "[[variables('workspaceResourceId')]" + }, + "identity": { + "type": "SystemAssigned" + }, + "apiVersion": "2017-07-01", + "dependsOn": [ + "[[resourceId('Microsoft.Web/connections', variables('AzureautomationConnectionName'))]", + "[[resourceId('Microsoft.Web/connections', variables('MicrosoftSentinelConnectionName'))]", + "[[resourceId('Microsoft.Web/connections', variables('KeyvaultConnectionName'))]" + ] + }, + { + "type": "Microsoft.Web/connections", + "apiVersion": "2016-06-01", + "name": "[[variables('AzureautomationConnectionName')]", + "location": "[[variables('workspace-location-inline')]", + "kind": "V1", + "properties": { + "displayName": "[[variables('AzureautomationConnectionName')]", + "parameterValueType": "Alternative", + "api": { + "id": "[[variables('_connection-2')]" + } + } + }, + { + "type": "Microsoft.Web/connections", + "apiVersion": "2016-06-01", + "name": "[[variables('MicrosoftSentinelConnectionName')]", + "location": "[[variables('workspace-location-inline')]", + "kind": "V1", + "properties": { + "displayName": "[[variables('MicrosoftSentinelConnectionName')]", + "parameterValueType": "Alternative", + "api": { + "id": "[[variables('_connection-3')]" + } + } + }, + { + "type": "Microsoft.Web/connections", + "apiVersion": "2016-06-01", + "name": "[[variables('KeyvaultConnectionName')]", + "location": "[[variables('workspace-location-inline')]", + "kind": "V1", + "properties": { + "displayName": "[[variables('KeyvaultConnectionName')]", + "parameterValueType": "Alternative", + "alternativeParameterValues": { + "token:TenantId": "[[variables('tenantId')]", + "token:grantType": "code", + "vaultName": "[[parameters('keyvaultName')]" + }, + "api": { + "id": "[[variables('_connection-4')]" + } + } + }, + { + "type": "Microsoft.OperationalInsights/workspaces/providers/metadata", + "apiVersion": "2022-01-01-preview", + "name": "[concat(parameters('workspace'),'/Microsoft.SecurityInsights/',concat('Playbook-', last(split(variables('playbookId1'),'/'))))]", + "properties": { + "parentId": "[variables('playbookId1')]", + "contentId": "[variables('_playbookContentId1')]", + "kind": "Playbook", + "version": "[variables('playbookVersion1')]", + "source": { + "kind": "Solution", + "name": "Commvault Security IQ", + "sourceId": "[variables('_solutionId')]" + }, + "author": { + "name": "svc.cv-securityiq@commvault.com" + }, + "support": { + "tier": "Partner", + "name": "Commvault", + "email": "support@commvault.com", + "link": "https://www.commvault.com/support" + } + } + } + ], + "metadata": { + "title": "Commvault Logic App Playbook", + "description": "This Logic App executes when called upon by an Automation Rule. Accessing the KeyVault to retrieve various credentials, it executes a specific runbook depending on the use case.", + "prerequisites": [ + "1. Administrative access to your Commvault/Metallic environment.", + "2. Administrative access to your Azure Resource Group and Subscription.", + "3. An Azure Sentinel instance in the aforementioned Azure Resource Group.", + "4. A Keyvault and an Automation Account configured as mentioned in the documentation here :- (https://github.com/Cv-securityIQ/Azure-Integration/blob/Commvault/Solutions/Commvault%20Security%20IQ/README.md)" + ], + "postDeployment": [ + "1. Steps to follow the instructions are mentioned here :- (https://github.com/Cv-securityIQ/Azure-Integration/blob/Commvault/Solutions/Commvault%20Security%20IQ/README.md)", + "2. Give the required permissions to the logic app to get the secrets from the keyvault.", + "3. Setup the Managed Identity" + ], + "lastUpdateTime": "2023-08-24T00:00:00Z", + "tags": [ + "Commvault", + "Metallic", + "Threat Intelligence", + "Ransomware", + "Security - Automation (SOAR)" + ], + "releaseNotes": { + "version": "1.0", + "title": "[variables('blanks')]", + "notes": [ + "Initial version" + ] + } + } + }, + "packageKind": "Solution", + "packageVersion": "[variables('_solutionVersion')]", + "packageName": "[variables('_solutionName')]", + "packageId": "[variables('_solutionId')]", + "contentSchemaVersion": "3.0.0", + "contentId": "[variables('_playbookContentId1')]", + "contentKind": "Playbook", + "displayName": "Commvault-Logic-App10", + "contentProductId": "[variables('_playbookcontentProductId1')]", + "id": "[variables('_playbookcontentProductId1')]", + "version": "[variables('playbookVersion1')]" + } + }, + { + "type": "Microsoft.OperationalInsights/workspaces/providers/contentPackages", + "apiVersion": "2023-04-01-preview", + "location": "[parameters('workspace-location')]", + "properties": { + "version": "3.0.0", + "kind": "Solution", + "contentSchemaVersion": "3.0.0", + "displayName": "Commvault Security IQ", + "publisherDisplayName": "Commvault", + "descriptionHtml": "

Note: There may be known issues pertaining to this Solution, please refer to them before installing.

\n

This Microsoft Sentinel integration enables Commvault users to ingest alerts and other data into their Microsoft Sentinel instance. With Analytic Rules, Microsoft Sentinel can automatically create Microsoft Sentinel incidents

\n

Analytic Rules: 3, Playbooks: 1

\n

Learn more about Microsoft Sentinel | Learn more about Solutions

\n", + "contentKind": "Solution", + "contentProductId": "[variables('_solutioncontentProductId')]", + "id": "[variables('_solutioncontentProductId')]", + "icon": "", + "contentId": "[variables('_solutionId')]", + "parentId": "[variables('_solutionId')]", + "source": { + "kind": "Solution", + "name": "Commvault Security IQ", + "sourceId": "[variables('_solutionId')]" + }, + "author": { + "name": "svc.cv-securityiq@commvault.com" + }, + "support": { + "name": "Commvault", + "email": "support@commvault.com", + "tier": "Partner", + "link": "https://www.commvault.com/support" + }, + "dependencies": { + "operator": "AND", + "criteria": [ + { + "kind": "AnalyticsRule", + "contentId": "[variables('analyticRulecontentId1')]", + "version": "[variables('analyticRuleVersion1')]" + }, + { + "kind": "AnalyticsRule", + "contentId": "[variables('analyticRulecontentId2')]", + "version": "[variables('analyticRuleVersion2')]" + }, + { + "kind": "AnalyticsRule", + "contentId": "[variables('analyticRulecontentId3')]", + "version": "[variables('analyticRuleVersion3')]" + }, + { + "kind": "Playbook", + "contentId": "[variables('_CommvaultLogicApp')]", + "version": "[variables('playbookVersion1')]" + } + ] + }, + "firstPublishDate": "2023-08-17", + "providers": [ + "Commvault" + ], + "categories": { + "domains": [ + "Security - Automation (SOAR)" + ] + } + }, + "name": "[concat(parameters('workspace'),'/Microsoft.SecurityInsights/', variables('_solutionId'))]" + } + ], + "outputs": {} +} diff --git a/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app1.png b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app1.png new file mode 100644 index 00000000000..0aaa7d968cf Binary files /dev/null and b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app1.png differ diff --git a/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app2.png b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app2.png new file mode 100644 index 00000000000..b834e1140bd Binary files /dev/null and b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app2.png differ diff --git a/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app3.png b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app3.png new file mode 100644 index 00000000000..e8b19100bfc Binary files /dev/null and b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app3.png differ diff --git a/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app4.png b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app4.png new file mode 100644 index 00000000000..bcd081ad2c7 Binary files /dev/null and b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/Images/Playbook_commvault_logic_app4.png differ diff --git a/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/azuredeploy.json b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/azuredeploy.json new file mode 100644 index 00000000000..2f2976753a8 --- /dev/null +++ b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/azuredeploy.json @@ -0,0 +1,428 @@ +{ + "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", + "contentVersion": "1.0.0.0", + "metadata": { + "title": "Commvault Logic App Playbook", + "description": "This Logic App executes when called upon by an Automation Rule. Accessing the KeyVault to retrieve various credentials, it executes a specific runbook depending on the use case.", + "prerequisites": ["1. Administrative access to your Commvault/Metallic environment.", + "2. Administrative access to your Azure Resource Group and Subscription.", + "3. An Azure Sentinel instance in the aforementioned Azure Resource Group.", + "4. A Keyvault and an Automation Account configured as mentioned in the documentation here :- (https://github.com/Cv-securityIQ/Azure-Integration/blob/Commvault/Solutions/Commvault%20Security%20IQ/README.md)"], + "postDeployment": ["1. Steps to follow the instructions are mentioned here :- (https://github.com/Cv-securityIQ/Azure-Integration/blob/Commvault/Solutions/Commvault%20Security%20IQ/README.md)", + "2. Give the required permissions to the logic app to get the secrets from the keyvault.", + "3. Setup the Managed Identity" + ], + "prerequisitesDeployTemplateFile": "", + "lastUpdateTime": "2023-08-24T00:00:00.000Z", + "entities": [], + "tags": [ "Commvault", "Metallic", "Threat Intelligence", "Ransomware", "Security - Automation (SOAR)" + ], + "support": { + "tier": "community", + "armtemplate": "Generated from https://github.com/Azure/Azure-Sentinel/tree/master/Tools/Playbook-ARM-Template-Generator" + }, + "author": { + "name": "microsoft" + } + }, + "parameters": { + "PlaybookName": { + "defaultValue": "Commvault-Logic-App10", + "type": "string" + }, + "Automation-Account": { + "defaultValue": "Commvault-Automation-Account", + "type": "string" + }, + "keyvaultName": { + "type": "string" + } + }, + "variables": { + "location": "[resourceGroup().location]", + "subscriptionId": "[subscription().subscriptionId]", + "tenantId": "[subscription().tenantId]", + "keyvaultApiId": "[concat('/subscriptions/', variables('subscriptionId'), '/providers/Microsoft.Web/locations/', variables('location'),'/managedApis/keyvault')]", + "AzureautomationConnectionName": "[concat('Azureautomation-', parameters('PlaybookName'))]", + "MicrosoftSentinelConnectionName": "[concat('MicrosoftSentinel-', parameters('PlaybookName'))]", + "KeyvaultConnectionName": "[concat('Keyvault-', parameters('PlaybookName'))]" + }, + "resources": [ + { + "properties": { + "provisioningState": "Succeeded", + "state": "Enabled", + "definition": { + "$schema": "https://schema.management.azure.com/providers/Microsoft.Logic/schemas/2016-06-01/workflowdefinition.json#", + "contentVersion": "1.0.0.0", + "parameters": { + "$connections": { + "defaultValue": { + }, + "type": "Object" + } + }, + "triggers": { + "Microsoft_Sentinel_incident": { + "type": "ApiConnectionWebhook", + "inputs": { + "body": { + "callback_url": "@{listCallbackUrl()}" + }, + "host": { + "connection": { + "name": "@parameters('$connections')['azuresentinel']['connectionId']" + } + }, + "path": "/incident-creation" + } + } + }, + "actions": { + "Access_Token": { + "runAfter": { + }, + "type": "ApiConnection", + "inputs": { + "host": { + "connection": { + "name": "@parameters('$connections')['keyvault']['connectionId']" + } + }, + "method": "get", + "path": "/secrets/@{encodeURIComponent('access-token')}/value" + } + }, + "Disable_Data_Aging": { + "actions": { + "Disable_Data_Aging_Job": { + "runAfter": { + }, + "type": "ApiConnection", + "inputs": { + "body": { + "properties": { + "parameters": { + "ClientName": "@triggerBody()?['object']?['properties']?['description']", + "EnvironmentEndpointURL": "@body('Environment_Endpoint_URL')?['value']", + "apiAccessToken": "@body('Access_Token')?['value']" + } + } + }, + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "put", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs", + "queries": { + "runbookName": "Commvault_Disable_Data_Aging", + "wait": true, + "x-ms-api-version": "2015-10-31" + } + } + }, + "Disable_Data_Aging_Job_Output": { + "runAfter": { + "Disable_Data_Aging_Job": [ + "Succeeded" + ] + }, + "type": "ApiConnection", + "inputs": { + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "get", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs/@{encodeURIComponent(body('Disable_Data_Aging_Job')?['properties']?['jobId'])}/output", + "queries": { + "x-ms-api-version": "2015-10-31" + } + } + } + }, + "runAfter": { + "Environment_Endpoint_URL": [ + "Succeeded" + ] + }, + "expression": { + "and": [ + { + "startsWith": [ + "@triggerBody()?['object']?['properties']?['description']", + "Data" + ] + } + ] + }, + "type": "If" + }, + "Disable_IDP": { + "actions": { + "Disable_IDP_Job": { + "runAfter": { + }, + "type": "ApiConnection", + "inputs": { + "body": { + "properties": { + "parameters": { + "EnvironmentEndpointURL": "@body('Environment_Endpoint_URL')?['value']", + "apiAccessToken": "@body('Access_Token')?['value']" + } + } + }, + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "put", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs", + "queries": { + "runbookName": "Commvault_Disable_IDP", + "wait": true, + "x-ms-api-version": "2015-10-31" + } + } + }, + "Disable_IDP_Job_Output": { + "runAfter": { + "Disable_IDP_Job": [ + "Succeeded" + ] + }, + "type": "ApiConnection", + "inputs": { + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "get", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs/@{encodeURIComponent(body('Disable_IDP_Job')?['properties']?['jobId'])}/output", + "queries": { + "x-ms-api-version": "2015-10-31" + } + } + } + }, + "runAfter": { + "Environment_Endpoint_URL": [ + "Succeeded" + ] + }, + "expression": { + "and": [ + { + "startsWith": [ + "@triggerBody()?['object']?['properties']?['description']", + "IDP" + ] + } + ] + }, + "type": "If" + }, + "Disable_User": { + "actions": { + "Disable_User_Job": { + "runAfter": { + }, + "type": "ApiConnection", + "inputs": { + "body": { + "properties": { + "parameters": { + "EnvironmentEndpointURL": "@body('Environment_Endpoint_URL')?['value']", + "UserIdentity": "@triggerBody()?['object']?['properties']?['description']", + "apiAccessToken": "@body('Access_Token')?['value']" + } + } + }, + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "put", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs", + "queries": { + "runbookName": "Commvault_Disable_User", + "wait": true, + "x-ms-api-version": "2015-10-31" + } + } + }, + "Disable_User_Job_Output": { + "runAfter": { + "Disable_User_Job": [ + "Succeeded" + ] + }, + "type": "ApiConnection", + "inputs": { + "host": { + "connection": { + "name": "@parameters('$connections')['azureautomation']['connectionId']" + } + }, + "method": "get", + "path": "/subscriptions/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['SubscriptionId'])}/resourceGroups/@{encodeURIComponent(triggerBody()?['workspaceInfo']?['ResourceGroupName'])}/providers/Microsoft.Automation/automationAccounts/@{encodeURIComponent('Commvault-Automation-Account')}/jobs/@{encodeURIComponent(body('Disable_User_Job')?['properties']?['jobId'])}/output", + "queries": { + "x-ms-api-version": "2015-10-31" + } + } + } + }, + "runAfter": { + "Environment_Endpoint_URL": [ + "Succeeded" + ] + }, + "expression": { + "and": [ + { + "startsWith": [ + "@triggerBody()?['object']?['properties']?['description']", + "User" + ] + } + ] + }, + "type": "If" + }, + "Environment_Endpoint_URL": { + "runAfter": { + "Access_Token": [ + "Succeeded" + ] + }, + "type": "ApiConnection", + "inputs": { + "host": { + "connection": { + "name": "@parameters('$connections')['keyvault']['connectionId']" + } + }, + "method": "get", + "path": "/secrets/@{encodeURIComponent('environment-endpoint-url')}/value" + } + } + }, + "outputs": { + } + }, + "parameters": { + "$connections": { + "value": { + "azureautomation": { + "connectionId": "[resourceId('Microsoft.Web/connections', variables('AzureautomationConnectionName'))]", + "connectionName": "[variables('AzureautomationConnectionName')]", + "id": "[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/Azureautomation')]", + "connectionProperties": { + "authentication": { + "type": "ManagedServiceIdentity" + } + } + }, + "azuresentinel": { + "connectionId": "[resourceId('Microsoft.Web/connections', variables('MicrosoftSentinelConnectionName'))]", + "connectionName": "[variables('MicrosoftSentinelConnectionName')]", + "id": "[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/Azuresentinel')]", + "connectionProperties": { + "authentication": { + "type": "ManagedServiceIdentity" + } + } + }, + "keyvault": { + "connectionId": "[resourceId('Microsoft.Web/connections', variables('KeyvaultConnectionName'))]", + "connectionName": "[variables('KeyvaultConnectionName')]", + "id": "[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/Keyvault')]", + "connectionProperties": { + "authentication": { + "type": "ManagedServiceIdentity" + } + } + } + } + } + } + }, + "name": "[parameters('PlaybookName')]", + "type": "Microsoft.Logic/workflows", + "location": "[resourceGroup().location]", + "tags": { + "hidden-SentinelTemplateName": "Commvault-Logic-App1", + "hidden-SentinelTemplateVersion": "1.0" + }, + "identity": { + "type": "SystemAssigned" + }, + "apiVersion": "2017-07-01", + "dependsOn": [ + "[resourceId('Microsoft.Web/connections', variables('AzureautomationConnectionName'))]", + "[resourceId('Microsoft.Web/connections', variables('MicrosoftSentinelConnectionName'))]", + "[resourceId('Microsoft.Web/connections', variables('KeyvaultConnectionName'))]" + ] + }, + { + "type": "Microsoft.Web/connections", + "apiVersion": "2016-06-01", + "name": "[variables('AzureautomationConnectionName')]", + "location": "[resourceGroup().location]", + "kind": "V1", + "properties": { + "displayName": "[variables('AzureautomationConnectionName')]", + "customParameterValues": { + }, + "parameterValueType": "Alternative", + "api": { + "id": "[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/Azureautomation')]" + } + } + }, + { + "type": "Microsoft.Web/connections", + "apiVersion": "2016-06-01", + "name": "[variables('MicrosoftSentinelConnectionName')]", + "location": "[resourceGroup().location]", + "kind": "V1", + "properties": { + "displayName": "[variables('MicrosoftSentinelConnectionName')]", + "customParameterValues": { + }, + "parameterValueType": "Alternative", + "api": { + "id": "[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/Azuresentinel')]" + } + } + }, + { + "type": "Microsoft.Web/connections", + "apiVersion": "2016-06-01", + "name": "[variables('KeyvaultConnectionName')]", + "location": "[resourceGroup().location]", + "kind": "V1", + "properties": { + "displayName": "[variables('KeyvaultConnectionName')]", + "customParameterValues": { + }, + "parameterValueType": "Alternative", + "alternativeParameterValues": { + "token:TenantId": "[variables('tenantId')]", + "token:grantType": "code", + "vaultName": "[parameters('keyvaultName')]" + }, + "api": { + "id": "[concat('/subscriptions/', subscription().subscriptionId, '/providers/Microsoft.Web/locations/', resourceGroup().location, '/managedApis/Keyvault')]" + } + } + } + ] +} diff --git a/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/readme.md b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/readme.md new file mode 100644 index 00000000000..33e6d0d99a8 --- /dev/null +++ b/Solutions/Commvault Security IQ/Playbooks/CommvaultLogicApp/readme.md @@ -0,0 +1,26 @@ +# Commvault Logic App Playbook +## Summary +This Logic App executes when called upon by an Automation Rule. Accessing the KeyVault to retrieve various credentials, it executes a specific runbook depending on the use case. + +## Prerequisites +- Administrative access to your Commvault/Metallic environment. +- Administrative access to your Azure Resource Group and Subscription. +- An Azure Sentinel instance in the aforementioned Azure Resource Group. +- A Keyvault and an Automation Account configured as mentioned in the documentation here :- (https://github.com/Cv-securityIQ/Azure-Integration/blob/Commvault/Solutions/Commvault%20Security%20IQ/README.md) + +## Deployment Instructions +Deploy the playbook by clicking on "Deploy to Azure" button. This will take you to deploying an ARM Template wizard. + +[![Deploy to Azure](https://aka.ms/deploytoazurebutton)](https://portal.azure.com/#create/Microsoft.Template/uri/https%3A%2F%2Fraw.githubusercontent.com%2FAzure%2FAzure-Sentinel%2Fmaster%2FSolutions%2Commvault%20Security%20IQ%2FPlaybooks%2CommvaultLogicApp%2Fazuredeploy.json) +[![Deploy to Azure Gov](https://aka.ms/deploytoazuregovbutton)](https://portal.azure.us/#create/Microsoft.Template/uri/https%3A%2F%2Fraw.githubusercontent.com%2FAzure%2FAzure-Sentinel%2Fmaster%2FSolutions%2Commvault%20Security%20IQ%2FPlaybooks%2CommvaultLogicApp%2Fazuredeploy.json) + +Alternatively:- +1. To import the logic app from the azure portal go to "Custom Deployment" +2. "Build your own template in the editor" +3. "Load File" -> Use the json present under **Playbooks/CommvaultLogicApp/azuredeploy.json**. +4. Enter in the required parameters + +## Post-deployment Instructions +Steps to follow the instructions are mentioned here :- (https://github.com/Cv-securityIQ/Azure-Integration/blob/Commvault/Solutions/Commvault%20Security%20IQ/README.md) +1. Give the required permissions to the logic app to get the secrets from the keyvault. +2. Setup the Managed Identity diff --git a/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Cycle_Token.ps1 b/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Cycle_Token.ps1 new file mode 100644 index 00000000000..7b2089b6462 --- /dev/null +++ b/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Cycle_Token.ps1 @@ -0,0 +1,81 @@ +<# Input Parameters #> +Param( +[Parameter(Mandatory = $true)] +[String] $apiAccessToken, + +[Parameter(Mandatory = $true)] +[String] $EnvironmentEndpointURL, + +[Parameter(Mandatory = $true)] +[String] $keyVaulturl, + +[Parameter(Mandatory = $true)] +[String] $keyVaultTenantID, + +[Parameter(Mandatory = $true)] +[String] $keyVaultClientID, + +[Parameter(Mandatory = $true)] +[String] $keyVaultClientSecret +) +<# End Input Parameters #> + +<# Global Variables #> +$headers = @{} +$headers.add("Accept", "application/json") +$headers.add("Content-Type", "application/json") +$authToken = "QSDK " + $apiAccessToken +$headers.add("Authtoken", $authToken) +<# End of Global Variables #> + +<# Get the current date and time as a Unix timestamp #> +$currentUnixTime = [int][double]::Parse((Get-Date -UFormat %s)) + +<# Add 7 days in seconds (7 * 24 * 60 * 60) #> +$sevenDaysInSeconds = 604800 + +<# Add 7 days to the current Unix timestamp #> +$desiredTimeUNIXtimestamp = $currentUnixTime + $sevenDaysInSeconds + +<# Generate unique AccessToken name that contain creation and expiry timestamp #> +$newTokenName = "soar-crt$currentUnixTime-exp$desiredTimeUNIXtimestamp" + +<# Create new API AccessToken #> +$body = @{ + tokenExpires = @{ + time = $desiredTimeUNIXtimestamp + } + scope = 2 + tokenName = $newTokenName +} | ConvertTo-Json +$generateAccessTokenURL = "https://$EnvironmentEndpointURL/commandcenter/api/ApiToken/User" +$generateAccessTokenResult = Invoke-RestMethod $generateAccessTokenURL -Method POST -Headers $headers -Body $body + +<# If the new access token was generated, set it in KeyVault #> +$newAccessToken = $null +$newAccessToken = $generateAccessTokenResult.token +if ($newAccessToken -ne $null) { + $url = "https://login.microsoftonline.com/$keyVaultTenantId/oauth2/token" + $headers = @{ + "Content-Type" = "application/x-www-form-urlencoded" + } + $data = @{ + "grant_type" = "client_credentials" + "client_id" = $keyVaultClientID + "client_secret" = $keyVaultClientSecret + "resource" = "https://vault.azure.net" + } + $response = Invoke-RestMethod -Uri $url -Method POST -Body $data -Headers $headers + $keyvault_access_token = $response.access_token + $endpoint = "$keyVaultUrl/secrets/access-token?api-version=7.2" + $headers = @{ + "Authorization" = "Bearer $keyvault_access_token" + "Content-Type" = "application/json" + } + $body = @{ + "value" = $newAccessToken + } + $response = Invoke-RestMethod -Uri $endpoint -Method PUT -Body ($body | ConvertTo-Json) -Headers $headers -ContentType 'application/json' + Write-Output $response.value +} +else { Write-Output "FAIL. Could not generate a new access token." } \ No newline at end of file diff --git a/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Disable_Data_Aging.ps1 b/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Disable_Data_Aging.ps1 new file mode 100644 index 00000000000..b11f10846b4 --- /dev/null +++ b/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Disable_Data_Aging.ps1 @@ -0,0 +1,103 @@ +<# Input Variables #> +<# $EnvironmentEndpointURL = Read-Host -Prompt 'Input Metallic RingURL / Commvault endpoint URL / examples: m102.metallic.io | 10.0.0.5' #> +<# $apiAccessToken = Read-Host -Prompt 'Input Commvault RestAPI user AccessToken' #> +<# $clientName = Read-Host -Prompt 'Input Server Hostname or ClientName' #> + +Param( +[Parameter(Mandatory = $true)] +[String] $apiAccessToken, + +[Parameter(Mandatory = $true)] +[String] $EnvironmentEndpointURL, + +[Parameter(Mandatory = $true)] +[String] $clientName +) + + +<# End of Input Variables #> + +<# Global Variables #> +$headers = @{} +$headers.add("Accept", "application/json") +$headers.add("Content-Type","application/json") +$authToken = "QSDK "+$apiAccessToken +$headers.add("Authtoken",$authToken) +<# End of Global Variables #> + +<# Get all Tenant Clients #> +$getClientsURL = "https://$EnvironmentEndpointURL/commandcenter/api/client" +$getClientsResult = Invoke-RestMethod $getClientsURL -Method GET -Headers $headers + +<# End of Get all Tenant Clients #> + +<# Add wildcard (on the end) to Server Input to address scenario that server short name would be given and we have full FQDN or if there is additon on our ClientName like (1) #> +$clientName = $clientName + "*" +<# Select all Clients that match Input Server Hostname or ClientName #> +$selectedClients = @() +foreach ($client in $getClientsResult.clientProperties.client.clientEntity | Where-Object { $_.hostname -like $clientName -or $_.clientName -like $clientName}) { + $selectedClients += New-Object PSObject -Property @{ + ClientName = $client.clientName + ClientHostname = $client.hostname + ClientID = $client.ClientId + } +} + +<# Check if Clients array is not empty | if anything was matched in previous step #> +if ($selectedClients -ne "") { + + <# Print matched Clients for referance #> + Write-Output "Following Client(s) were found that match input Server Hostname or ClientName" + Write-Output $selectedClients + Write-Output "------------------------------" + +<# Start flow for each matched Client in array #> +foreach ($selectedclient in $selectedClients) { + <# Get attributes as ID, ClientName and Hostname from matched Clients array for current Client #> + $selectedclientId = $selectedclient.ClientId + $selectedclientName = $selectedclient.ClientName + $selectedclientHostname = $selectedclient.ClientHostname + <# Get Client Properties and Archive Pruning Status #> + $getClientPropURL = "https://$EnvironmentEndpointURL/commandcenter/api/client/$selectedclientId" + $getClientPropResult = Invoke-RestMethod $getClientPropURL -Method GET -Headers $headers + $getClientActivityControlOptions = $getClientPropResult.clientProperties.clientProps.clientActivityControl.activityControlOptions + $getClientActivityType16ControlOptions = ($getClientActivityControlOptions | Where-Object { $_.activityType -eq 16 }) + $clientArchivePruningStatus = $getClientActivityType16ControlOptions.enableActivityType + + <# Check what is Archive Pruning Status and perform relevant action #> + <# First check if Archive Pruning Status is Enabled and then Disable it #> + if ($clientArchivePruningStatus -eq $true) { + + $body = "{ + `n `"clientProperties`": { + `n `"clientProps`": { + `n `"clientActivityControl`": { + `n `"activityControlOptions`": [ + `n { + `n `"activityType`": 16, + `n `"enableAfterADelay`": false, + `n `"enableActivityType`": false + `n } + `n ] + `n } + `n } + `n } + `n}" + $disableClientArchivePruningURL = "https://$EnvironmentEndpointURL/commandcenter/api/client/$selectedclientId" + $disableClientArchivePruningResult = Invoke-RestMethod $getClientPropURL -Method POST -Headers $headers -Body $body + $disableClientArchivePruningResultErrorCode = $disableClientArchivePruningResult.response.errorCode + <# Check status of operation to Disable Archive Pruning Status and print relevant message #> + if ($disableClientArchivePruningResultErrorCode -eq 0) { + Write-Output "Archive Pruning succesfully Disabled for Client $selectedclientName (Hostname: $selectedclientHostname)" + } else {Write-Output "Something went wrong. Error code $disableClientArchivePruningResultErrorCode do not indicate success for disabling Archive Pruning on Client $selectedclientName (Hostname: $selectedclientHostname)"} + <# In case Archive Pruning Status is already Disabled print status #> + } elseif ($clientArchivePruningStatus -eq $false) { + Write-Output "Archive Pruning is already Disabled for Client $selectedclientName (Hostname: $selectedclientHostname). No further action taken." + <# In case there was a problem with getting Archive Pruning Status print error message #> + } else {Write-Output "Something went wrong. Unable to retrieve Archive Pruning status for Client $selectedclientName (Hostname: $selectedclientHostname)"} +} + +<# In case Clients array is empty print eror message #> +} else { + Write-Output "Something went wrong. No Client(s) found" +} \ No newline at end of file diff --git a/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Disable_IDP.ps1 b/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Disable_IDP.ps1 new file mode 100644 index 00000000000..253a7cb06f9 --- /dev/null +++ b/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Disable_IDP.ps1 @@ -0,0 +1,53 @@ +<# Input Variables #> +<# $EnvironmentEndpointURL = Read-Host -Prompt 'Input Metallic RingURL / Commvault endpoint URL / examples: m102.metallic.io | 10.0.0.5' #> +<# $apiAccessToken = Read-Host -Prompt 'Input Commvault RestAPI user AccessToken' #> + +Param( +[Parameter(Mandatory = $true)] +[String] $apiAccessToken, + +[Parameter(Mandatory = $true)] +[String] $EnvironmentEndpointURL +) + +<# Global Variables #> +$headers = @{} +$headers.add("Accept", "application/json") +$headers.add("Content-Type","application/json") +$authToken = "QSDK "+$apiAccessToken +$headers.add("Authtoken",$authToken) +<# End of Global Variables #> + +<# Get all Tenant Identity Servers #> +$getIdentityServersURL = "https://$EnvironmentEndpointURL/commandcenter/api/IdentityServers" +$getIdentityServersResult = Invoke-RestMethod $getIdentityServersURL -Method GET -Headers $headers +<# End of Get all Tenant Identity Servers #> + +<# Filter Identity Servers that are SAML type #> +$samlIdentityServers = $getIdentityServersResult.identityServers | Where-Object { $_.samlType -eq 1} +<# For each SAML Identity Server go with steps to check it's state and take action #> +foreach ($samlIdentityServer in $samlIdentityServers) { + + <# Gets details of SAML Identity Server #> + $samlIdentityServerName = $samlIdentityServer.IdentityServerName + $getsamlIdentityServerPropURL = "https://$EnvironmentEndpointURL/commandcenter/api/V4/SAML/$samlIdentityServerName" + $getsamlIdentityServerPropResult = Invoke-RestMethod $getsamlIdentityServerPropURL -Method GET -Headers $headers + + <# Check if SAML Identity Server is enabled or disabled and take action or give status #> + if ($getsamlIdentityServerPropResult.enabled -eq $true) { + Write-Output "Going to disable IDP server $samlIdentityServerName" + <# Disable SAML Identity Server if it is enabled #> + $body = "{`"enabled`": false, `"type`": `"SAML`"}" + $disablesamlIdentityServerURL = "https://$EnvironmentEndpointURL/commandcenter/api/V4/SAML/$samlIdentityServerName" + $disablesamlIdentityServerResult = Invoke-RestMethod $disablesamlIdentityServerURL -Method PUT -Headers $headers -Body $body + $disablesamlIdentityServerResulterrorCode = $disablesamlIdentityServerResult.errorCode + <# Based on response error code verify if action was succesfull and return status #> + if ($disablesamlIdentityServerResulterrorCode -eq 0) { + Write-Output "SAML IdentityProvider $samlIdentityServerName succesfully disabled" + } else {"Something went wrong. Error code $disablesamlIdentityServerResulterrorCode for disabling SAML IdentityProvider $samlIdentityServerName action do not indicate success"} + <# In case SAML Identity Server is alredy disabled return status #> + } elseif ($getsamlIdentityServerPropResult.enabled -eq $false) { + Write-Output "SAML IdentityProvider $samlIdentityServerName is already disabled. No action taken" + <# In case SAML Identity Server disabled/enabled state is not correctly retrieved return status #> + } else {Write-Output "Something went wrong. Unable to retrieve state for SAML IdentityProvider $samlIdentityServerName"} +} \ No newline at end of file diff --git a/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Disable_User.ps1 b/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Disable_User.ps1 new file mode 100644 index 00000000000..348aac93e6e --- /dev/null +++ b/Solutions/Commvault Security IQ/Playbooks/Runbooks/Commvault_Disable_User.ps1 @@ -0,0 +1,66 @@ +<# Input Variables #> +<# $EnvironmentEndpointURL = Read-Host -Prompt 'Input Metallic RingURL / Commvault endpoint URL / examples: m102.metallic.io | 10.0.0.5' #> +<# $apiAccessToken = Read-Host -Prompt 'Input Commvault RestAPI user AccessToken' #> +<# $userIdentity = Read-Host -Prompt 'Enter User email or UPN' #> + +Param( +[Parameter(Mandatory = $true)] +[String] $apiAccessToken, + +[Parameter(Mandatory = $true)] +[String] $EnvironmentEndpointURL, + +[Parameter(Mandatory = $true)] +[String] $userIdentity +) + +<# End of Input Variables #> + +<# Extract the userIdentity from the given userIdentity string #> + +<# End of extraction #> + +<# Global Variables #> +$headers = @{} +$headers.add("Accept", "application/json") +$headers.add("Content-Type","application/json") +$authToken = "QSDK "+$apiAccessToken +$headers.add("Authtoken",$authToken) +<# End of Global Variables #> + +<# Get all Tenant Users #> +$getUsersURL = "https://$EnvironmentEndpointURL/commandcenter/api/User?level=10" +$getUsersResult = Invoke-RestMethod $getUsersURL -Method GET -Headers $headers +<# End of Get all Tenant Users #> + +<# Select User based on email or UPN #> +$selectedUserID = "Empty" +$selectedUser = $getUsersResult.users | Where-Object { $_.email -eq $userIdentity -or $_.UPN -eq $userIdentity} +if ($selectedUser.email -eq $userIdentity -or $selectedUser.UPN -eq $userIdentity){ + $selectedUserID = $selectedUser.userEntity[0].userId +} else {Write-Output "User $userIdentity was not found"; Exit} +<# End of Select User based on email or UPN #> + +<# Get selected user details #> +$getSelectedUserDetailsURL = "https://$EnvironmentEndpointURL/commandcenter/api/User/$selectedUserID" +$getSelectedUserDetailsResult = Invoke-RestMethod $getSelectedUserDetailsURL -Method GET -Headers $headers +<# End of Get selected user details #> + +<# Check user if user is enabled and take action #> +if ($getSelectedUserDetailsResult.users.enableUser -eq $true) { + $disableUserURL = "https://$EnvironmentEndpointURL/commandcenter/api/User/$selectedUserID/Disable" + $disableUserResult = Invoke-RestMethod $disableUserURL -Method PUT -Headers $headers + $disableUserResulterrorCode = $disableUserResult.response.errorCode + if ($disableUserResulterrorCode -eq 0) {Write-Output "User $userIdentity was succesfully disabled"} else { + Write-Output "Something went wrong. Error code $disableUserResulterrorCode for disabling User account $userIdentity do not indicate success." + } +} elseif ($getSelectedUserDetailsResult.users.enableUser -eq $false) { + Write-Output "User $userIdentity is already disabled. No action taken." + } else {Write-Output "Something went wrong. Cannot retrieve status for user $userIdentity"} +<# End of Check user if user is enabled and take action #> + +<# Get Selected User Sessions #> +$getSelectedUserSessionsURL = "https://$EnvironmentEndpointURL/commandcenter/api/Session?userId=$selectedUserID" +$getSelectedUserSessionsResult = Invoke-RestMethod $getSelectedUserSessionsURL -Method GET -Headers $headers +$expectedSelectedUserSessionsResult="*" +<# End of Get Selected User Sessions #> \ No newline at end of file diff --git a/Solutions/Commvault Security IQ/README.md b/Solutions/Commvault Security IQ/README.md new file mode 100644 index 00000000000..34be44e0938 --- /dev/null +++ b/Solutions/Commvault Security IQ/README.md @@ -0,0 +1,604 @@ +# Commvault -- Sentinel Integration +This Sentinel integration enables Commvault users to ingest alerts and other data into their Sentinel instance. With Analytic Rules, Sentinel can automatically create Sentinel incidents from incoming Commvault syslogs. + +### Key Features +- Using Azure KeyVault, Commvault access tokens are automatically rotated, providing enhanced security. +- Perform automated actions such as disabling IDP, specific users, or data aging on your Commvault/Metallic environment from inside Sentinel. + +## Prerequisites +- Administrative access to your Commvault/Metallic environment. +- Administrative access to your Azure Resource Group and Subscription. +- An Azure Sentinel instance in the aforementioned Azure Resource Group. +- An Azure Log Analytic Workspace in the aformentioned Azure Resource Group. + +## Inventory of Required Assets +The following Azure assets need to all be created in order for this integration to function properly. In addition to these assets, proper permissions need to be granted. When following the installation instructions, please use the same asset names to ensure compatibility. +### Automation Account +- **Commvault-Automation-Account:** This is where the runbooks are stored. +### Runbooks +All runbooks are stored in the Automation Account *Commvault-Automation-Account*. +- **Commvault_Cycle_Token:** Used in the *CommvaultTokenCycle* Logic App to execute the API calls that generate a new Commvault/Metallic access token. +- **Commvault_Disable_Data_Aging:** Used in the *Commvault-Logic-App* Logic App to execute the API calls that disable data aging for a specific client. +- **Commvault_Disable_IDP:** Used in the *Commvault-Logic-App* Logic App to execute the API calls that disable the IDP in your environment. +- **Commvault_Disable_User:** Used in the *Commvault-Logic-App* Logic App to execute the API calls that disable a specific user given their email address. +### Logic Apps +- **Commvault-Logic-App:** This Logic App (also referred to as a *Playbook*) executes when called upon by an Automation Rule. Accessing the KeyVault to retrieve various credentials, it executes a specific runbook depending on the use case. +- **CommvaultTokenCycle:** This Logic App (also referred to as a *Playbook*) executes periodically to generate a new Commvault/Metallic access token and securely overwrites the old access token in your KeyVault. +### KeyVaults +- **Commvault-Integration-KV:** This KeyVault stores all required credentials as *secrets*. +### KeyVault Secrets +All of these secrets are stored in the *Commvault-IntegrationKV* KeyVault. For the first time setup, their values need to be manually retrieved. +- **access-token:** The access token for Commvault/Metallic. +- **environment-endpoint-url:** The URL of your Commvault/Metallic endpoint. +- **keyvault-url:** The URL of your Azure KeyVault. +- **client-id:** The ID of the Azure App Registration client. +- **tenant-id:** The ID of your Azure Tenant. +- **secret-id:** The ID of your Azure App Registration client secret. +- **keyvaultsecret:** The value of your Azure App Registration client secret. +### App Registrations +- **Commvault_Token_Cycle_App:** An Azure Active Directory App Registration used for authorized KeyVault access. +### Sentinel Analytic Rules +Each of these Analytic Rules run on a continuous basis and are querying for the manually triggered Sentinel incident. Once it discovers a specific incident, a new incident is created that triggers the corresponding Automation Rule. +- **IDP Compromised:** The Sentinel Analytic Rule that continuously searches for a manually created Sentinel Incident pertaining to a compromised Commvault/Metallic IDP. +- **User Compromised:** The Sentinel Analytic Rule that continuously searches for a manually created Sentinel Incident pertaining to a compromised Commvault/Metallic user. +- **Data Aging:** The Sentinel Analytic Rule that continuously searches for a manually created Sentinel Incident pertaining to a request to disable data aging on a specific Commvault/Metallic client. + +## Installation +### Create the Runbooks +* Go to Automation Accounts -> Create + * Basics: + * Select the correct subscription and resource group + * Name it “Commvault-Automation-Account" + * Click “Create” +* Go to “Commvault-Automation-Account" -> Runbooks (under “Process Automation”) -> Create a Runbook + * Name = + * Commvault_Disable_IDP + * Runbook Type = + * Powershell + * Runtime Version = + * 5.1 + * Click “Create” + * Edit Powershell Runbook = + * Use the content in this file: **Runbooks/Commvault_Disable_IDP.ps1** + * Click "Publish" + * Click "Save" +* Go to “Commvault-Automation-Account" -> Runbooks (under “Process Automation”) -> Create a Runbook + * Name = + * Commvault_Disable_User + * Runbook Type = + * Powershell + * Runtime Version = + * 5.1 + * Click "Create" + * Edit Powershell Runbook = + * Use the content in this file: **Runbooks/Commvault_Disable_Users.ps1** + * Click "Publish" + * Click "Save" +* Go to “Commvault-Automation-Account" -> Runbooks (under “Process Automation”) -> Create a Runbook + * Name = + * Commvault_Disable_Data_Aging + * Runbook Type = + * Powershell + * Runtime Version = + * 5.1 + * Click "Create" + * Edit Powershell Runbook = + * Use the content in this file: **Runbooks/Commvault_Disable_Data_Aging.ps1** + * Click "Publish" + * Click "Save" + +### Create The KeyVault: +* Go to KeyVault -> Create + * Basics: + * Select the correct subscription and resource group + * KeyVault name = + * Commvault-Integration-KV + +### Create the KeyVault Secrets: +* Go to KeyVault -> "Commvault-Integration-KV" -> Secrets (Under "Objects") -> "Generate/Import" + * Upload Options: + * Manual + * Name: + * access-token + * Secret Value: + * (Your Commvault/Metallic access token) + * Enabled: + * Yes + * Click "Create" +* Go to KeyVault -> "Commvault-Integration-KV" -> Secrets (Under "Objects") -> "Generate/Import" + * Upload Options: + * Manual + * Name: + * environment-endpoint-url + * Secret Value: + * (Your Commvault/Metallic endpoint's URL) + * Enabled: + * Yes + * Click "Create" + +### Initialize the Logic App (*Playbook*): +* Go to "Custom Deployment" -> "Build your own template in the editor" -> "Load File" -> Use the json present under **Playbooks/CommvaultLogicApp/azuredeploy.json**. + * Save + * Enter the resource group, subscription, automation account and keyvault name + * In the playbook name field use "Commvault-Logic-App" +* Go to KeyVault -> Commvault-Integration-KV +* Access Configuration: + * Permission Model = + * Vault Access Policy + * Go to "Access Policies" -> "Create" + * Under "Permissions" -> "Secret Permissions" + * Select "Get", "List", and "Set" + * Click "Next" + * Under "Principal" + * Search for "Commvault-Logic-App" + * Select "Commvault-Logic-App from the search results + * Click "Next" + * Under "Application (Optional)" + * Do nothing here except click "Next" + * Under "Review + Create" + * Click "Create" + * Click "Review + Create" + * Click "Create" + +### Setup the Managed Identity +* Go to Automation Accounts -> "Commvault-Sandbox-Automation-Account" -> "Access Control (IAM)" -> "Add" -> "Add Role Assignment + * In "Job function roles" under "role": + * Click on "Automation Contributor" so that it is highlighted in grey + * Click "Next" + * Assign Access To: + * Select "Managed Identity" + * Members: + * Select "Select Members" + * Select the correct subscription + * For Managed Identity, select "Logic App" + * Select "Commvault-Logic-App" form the list + * Click the blue "select" button + * Go to the "Review + Assign" tab + * Click the blue "Review + Assign" button +* Go to your resource group -> "Access Control (IAM)" -> "Add" -> "Add Role Assignment" + * In "Job Function Roles" under "Role" + * Find "Microsoft Sentinel Automation Contributor" and click it so that it is highlighted in grey + * Under the "Members" tab + * Assign access to: + * Managed Identity + * Click "+ Select Members" + * Select the correct subscription + * Managed Identity: + * Logic App + * From the list, select "Commvault-Logic-App" + * Click the blue "Select" button + * Under "Review + Assign" tab + * Click the blue "Review + Assign" button +* Go to "Logic Apps" -> "Commvault-Logic-App" -> "Identity" (under "Settings") -> "System Assigned" tab -> "Azure Role Assignments" + * Add Role Assignment + * Scope: + * KeyVault + * Resource: + * Commvault-Integration-KV + * Role: + * KeyVault Secrets Officer + * Click the blue "Save" button + +### Create the Analytic Rules: +* Go to Sentinel -> (The name of your Sentinel instance) -> Analytics (located under “Configuration”) -> Create -> Scheduled Query Rule + * General: + * Name: + * IDP Alert + * Description: + * IDP Compromised + * Set Rule Logic: + * Rule Query: + SecurityIncident + | where Title has "Cvlt Alert" + and Description == "IDP Compromised" + and Status has "New" + * Run Query Every: + * 5 minutes + * Lookup data from the last: + * 5 minutes + * Incident Settings: + * Alert Grouping: + * Enabled + * Review and Create: + * Create +* Go to Sentinel -> (The name of your Sentinel instance) -> Analytics (located under “Configuration”) -> Create -> Scheduled Query Rule + * General: + * Name: + * Data Alert + * Description: + * Data Compromised + * Set Rule Logic: + * Rule Query: + SecurityIncident + | where Title has "Cvlt Alert" and Description has "Client" and Description has "Compromised" and Status has "New" + | extend extracted_word = extract("Client\\s(.*?)\\sCompromised", 1, Description) + | project TimeGenerated, + Title, + Description, + Status, + CustomDetails = extracted_word + * Alert Details: + * Alert Name Format: + * User Alert + * Alert Description Format: + * {{Custom Details}} + * Run Query Every: + * 5 minutes + * Lookup data from the last: + * 5 minutes + * Incident Settings: + * Alert Grouping: + * Enabled + * Review and Create: + * Create +* Go to Sentinel -> (The name of your Sentinel instance) -> Analytics (located under “Configuration”) -> Create -> Scheduled Query Rule + * General: + * Name: + * User Alert + * Description: + * User Compromised + * Set Rule Logic: + * Rule Query: + SecurityIncident + | where Title has "Cvlt Alert" and Description has "User" and Description has "Compromised" and Status has "New" + | extend extracted_word = extract("User\\s(.*?)\\sCompromised", 1, Description) + | project TimeGenerated, + Title, + Description, + Status, + CustomDetails = extracted_word + * Alert Details: + * Alert Format: + * User Alert + * Alert Description Format: + * {{CustomDetails}} + * Run Query Every: + * 5 minutes + * Lookup data from the last: + * 5 minutes + * Incident Settings: + * Alert Grouping: + * Enabled + * Review and Create + * Create +### Create The Automation Rules +* Go to Sentinel -> (The name of your Sentinel instance) -> Automation (located under “Configuration”) -> Create -> Automation Rule + * Automation Rule Name: + * Commvault-Disable-Data-Aging-Rule + * Trigger: + * When incident is created + * Conditions: + * If incident provider: + * Equals + * Microsoft Sentinel + * Analytic Rule Name: + * Contains + * Data Alert + * In the box in the "Actions" section, select "Change Status" + * In the box below "Change Status" in the "Actions" section, select "Closed" + * In the box below that, select "True Positive - Suspicious Activity" + * At the bottom of the "Actions" section, click "+ Add Action" + * As an owner of the resource group, click the blue "Manage Playbook Permissions" text + * Select your resource group + * Click "Apply" + * Click the box below "Run Playbook" in the "Actions" section + * Select "Commvault-Logic-App" + * Order: + * 1 + * Click "Apply" +* Go to Sentinel -> (The name of your Sentinel instance) -> Automation (located under “Configuration”) -> Create -> Automation Rule + * Automation Rule Name: + * Commvault-Disable-IDP-Automation-Rule + * Trigger: + * When incident is created + * Conditions: + * If incident provider: + * Equals + * Microsoft Sentinel + * Analytic Rule Name: + * Contains + * IDP Alert + * In the box in the "Actions" section, select "Change Status" + * In the box below "Change Status" in the "Actions" section, select "Closed" + * In the box below that, select "True Positive - Suspicious Activity" + * At the bottom of the "Actions" section, click "+ Add Action" + * Click the box below "Run Playbook" in the "Actions" section + * Select "Commvault-Logic-App" + * Order: + * 2 + * Click "Apply" +* Go to Sentinel -> (The name of your Sentinel instance) -> Automation (located under “Configuration”) -> Create -> Automation Rule + * Automation Rule Name: + * Commvault-Disable-User-Automation-Rule + * Trigger: + * When incident is created + * Conditions: + * If incident provider: + * Equals + * Microsoft Sentinel + * Analytic Rule Name: + * Contains + * User Alert + * In the box in the "Actions" section, select "Change Status" + * In the box below "Change Status" in the "Actions" section, select "Closed" + * In the box below that, select "True Positive - Suspicious Activity" + * At the bottom of the "Actions" section, click "+ Add Action" + * Click the box below "Run Playbook" in the "Actions" section + * Select "Commvault-Logic-App" + * Order: + * 3 + * Click "Apply" +### Create the Active Directory App Registration: +* From Home, go to Azure Active Directory -> App Registrations (under “Manage”) +* In the top left corner, click “+ New Registration” + * Name: + * Commvault_Token_Cycle_App + * Click the blue "Register" button +* From Home, go to Azure Active Directory -> App Registrations (under “Manage”) +* Under “Owned Applications”, click on “Commvault_Token_Cycle_App” + * In the middle of the screen (under “Essentials”): + * Copy the “Application (client) ID” to another document. Hereon, this value will be referenced to as the App Registration Client ID. + * Copy the “Directory (tenant) ID” to another document. Hereon, this value will be referenced to as the Tenant ID. + * On the left (under “Manage”), click “API Permissions” + * In the middle of the screen, click “+ Add A Permission” + * In the right window that just popped open, select “Azure Key Vault” + * Under “Permissions”, select “user_impersonation” + * On the bottom of the screen, click the blue “Add Permissions” button + * On the left (under “Manage”), click “Certificates & Secrets” + * In the middle of the screen under “Client Secrets”, click “+ New Client Secret” + * Description: + * TokenCycle + * On the bottom of the screen, click the blue "Add" button + * In the table in the middle of the screen, copy the “Value” of the client secret “TokenCycle”. Copy this value to another document. Hereon, this value will be referenced to as the App Registration Client Secret. +### Define more KeyVault secrets: +* From Home, go to Key Vaults -> Commvault-Integration-KV +* In the middle of the screen, copy the “Vault URI” to another document. Hereon, this value will be referenced to as the KeyVault URL. +* Under “Objects” on the left, click “Secrets” + * On the top, click "+ Generate/Import" + * Name: + * client-id + * For "Secret Value", paste in the value of the App Registration Client ID + * On the top, click "+ Generate/Import" + * Name: + * keyvault-url + * For "Secret Value", paste in the KeyVault URL + * On the top, click "+ Generate/Import" + * Name: + * keyvaultsecret + * For "Secret Value", paste in the App Registration Client Secret + * On the top, click "+ Generate/Import" + * Name: + * tenant-id + * For "Secret Value", paste in the Tenant ID. +### Token Rotation Logic App: +* From Home, go to Logic Apps +* In the top left corner, click "+ Add" + * Basics: + * Project Details: + * Select your subscription and resource group + * Instance Details: + * Logic App Name: + * CommvaultTokenCycle + * Play Type: + * Consumption + * In the bottom left corner, click the blue "Review + Create" button +* In the "Logic App Designer" popup menu, select "Recurrence" Under "Start with a common trigger" +* In the "Recurrence" block: + * Interval: + * 5 + * Frequency: + * Days +* Save this by clicking the "Save" button in the top left corner. We will return to this later. +### Token Rotation Logic App Permissions: +* From Home, go to Logic Apps -> CommvaultTokenCycle + * On the left side, click on "Identity" (under "Settings") + * Under "System Assigned", switch "Status" to "On" + * Click "Save" (located just above the "Status" switch) + * If prompted, click "Yes" + * There should now be a blue "Azure Role Assignments" button. Click it. + * In the new page named "Azure Role Assignments", click "+ Add Role Assignment" + * Scope: + * KeyVault + * Subscription: + * (Your subscription) + * Resource: + * Commvault-Integration-KV + * Role: + * Key Vault Secrets Officer + * Click the blue "Save" button + * Click "+ Add Role Assignment" + * Scope: + * Resource Group + * Subscription: + * (Your subscription) + * Resource Group: + * (Your resource group) + * Role: + * Automation Runbook Operator + * Click the blue "Save" button + * Click "+ Add Role Assignment" + * Scope: + * Resource Group + * Subscription: + * (Your subscription) + * Resource Group: + * (Your resource group) + * Role: + * Microsoft Sentinel Contributor + * Click the blue "Save" button + * Click "+ Add Role Assignment" + * Scope: + * Resource Group + * Subscription: + * (Your subscription) + * Resource Group: + * (Your resource group) + * Role: + * Automation Contributor + * Click the blue "Save" button +### More KeyVault Permissions: +* From Home, go to KeyVaults -> Commvault-Integration-KV + * On the left pane, click "Access Policies" + * On the top left, click "+ Create" + * Permissions: + * Secret Permissions: + * Select "Get", "List", and "Set" + * Principal: + * Commvault_Token_Cycle_App + * Review + Create: + * Click the blue "Create" button on the bottom left + * On the top left, click "+ Create" + * Permissions: + * Secret Permissions: + * Select "Get", "List", and "Set" + * Principal: + * CommvaultTokenCycle + * Review + Create: + * Click the blue "Create" button on the bottom left +### Token Cycle Runbook: +* From Home, go to Automation Accounts -> Commvault-Automation-Account + * On the left pane, click “Runbooks” (under “Process Automation”) + * In the top left corner, click "+ Create a Runbook" + * Name: + * Commvault_Cycle_Token + * Runbook Type: + * PowerShell + * Runtime Version: + * 5.1 + * In the bottom left corner, click the blue "Create" button + * Copy and paste the content from **runbooks/Commvault_Cycle_Token.ps1** into the runbook editor + * In the top left, click "Save" + * In the top left, click "Publish" +### Completing the Token Rotation Logic App: +* From Home, go to Logic Apps -> CommvaultTokenCycle + * On the left pane, click "Logic App Designer" (located under "Development Tools") + * In the center of the screen (under the "Recurrence" block), click "+ New Step" + * Search for "get secret" + * Under All -> Actions, select "Get Secret - Azure KeyVault" + * Name of Secret: + * access-token + * Rename this block to be "Access Token" by clicking the three dots in the top right corner and selecting "Rename" + * In the center of the screen (under the "Access Token" block), click "+ New Step" + * Search for "get secret" + * Under All -> Actions, select "Get Secret - Azure KeyVault" + * Name of the secret + * environment-endpoint-url + * Rename this block to be "Endpoint URL" by clicking the three dots in the top right corner and selecting "Rename" + * In the center of the screen (under the "Endpoint URL" block), click "+ New Step" + * Search for "get secret" + * Under All -> Actions, select "Get Secret - Azure KeyVault" + * Name of the Secret: + * keyvault-url + * Rename this block to be "KeyVault URL" by clicking the three dots in the top right corner and selecting "Rename" + * In the center of the screen (under the "KeyVault URL" block), click "+ New Step" + * Search for "get secret" + * Under All -> Actions, select "Get Secret - Azure KeyVault" + * Name of the Secret + * tenant-id + * Rename this block to be "KeyVault Tenant ID" by clicking the three dots in the top right corner and selecting "Rename" + * In the center of the screen (under the "KeyVault Tenant ID" block), click "+ New Step" + * Search for "get secret" + * Under All -> Actions, select "Get Secret - Azure KeyVault" + * Name of the secret + * client-id + * Rename this block to be "KeyVault Client ID" by clicking the three dots in the top right corner and selecting "Rename" + * In the center of the screen (under the "KeyVault Client ID" block), click "+ New Step" + * Search for "get secret" + * Under All -> Actions, select "Get Secret - Azure KeyVault" + * Name of the Secret + * keyvaultsecret + * Rename this block to be "KeyVault Client Secret" by clicking the three dots in the top right corner and selecting "Rename" + * In the center of the screen (under the "KeyVault Client ID" block), click "+ New Step" + * Search for "create job" + * Under All -> Actions, select "Create Job - Azure Automation" + * Subscription: + * (Your subscription) + * Resource Group: + * (Your resource group) + * Automation Account: + * Commvault-Automation-Account + * Runbook Name: + * Commvault_Cycle_Token + * Wait for Job: + * Yes + * Runbook Parameter keyvaulturl: + * (The value of the "KeyVault URL" block) + * Runbook Parameter apiAccessToken: + * (The value of the "Access Token" block) + * Runbook Parameter EnvironmentEndpointURL: + * (The value of the "Endpoint URL" block) + * Runbook Parameter KeyVaultClientID: + * (The value of the "KeyVault Client ID" block) + * Runbook Parameter KeyVaultTenantID: + * (The value of the "KeyVault Tenant ID" block) + * Runbook Parameter KeyVaultClientSecret: + * (The value of the "KeyVault Client Secret" block) + * Rename this block to be "Cycle Token Job" by clicking the three dots in the top right corner and selecting "Rename" + * In the center of the screen (under the "cycle token job" block), click "+ New Step" + * Search for "get job output" + * Under All -> Actions, select "Get Job Output - Azure KeyVault" + * Subscription: + * (Your subscription) + * Resource Group: + * (Your resource group) + * Automation Account: + * Commvault-Automation-Account + * Job ID: + * (The job ID of "Cycle Token Job") + * In the top left corner, click "Save" + +## Example Usage +### Disable a compromised Commvault/Metallic IDP from Sentinel +* Go to Sentinel -> (The name of your Sentinel instance) -> Incidents (under Threat Management) -> Create Incident + * Title: + * Cvlt Alert + * Description: + * IDP Compromised + * Severity: + * Medium + * Status: + * New + * Click "Create" +* Wait 5-10 minutes for it to run +* Check if it ran: + * Go to Logic Apps -> Commvault-Logic-App + * In the middle of the screen is a table with the column headers Status, Start Time, etc. + * Sort the rows by start time by clicking the "Start Time" column header + * The latest run should say "Succeeded". Click it. + * Check to see the result of the runbook at the end of the logic app chain. +### Disable a compromised Commvault/Metallic User from Sentinel +* Go to Sentinel -> (The name of your Sentinel instance) -> Incidents (under Threat Management) -> Create Incident + * Title: + * Cvlt Alert + * Description (Where "< user email >" is the email address of the user that is compromised): + * User < user email > Compromised + * Severity: + * Medium + * Status: + * New + * Click "Create" +* Wait 5-10 minutes for it to run +* Check if it ran: + * Go to Logic Apps -> Commvault-Logic-App + * In the middle of the screen is a table with the column headers Status, Start Time, etc. + * Sort the rows by start time by clicking the "Start Time" column header + * The latest run should say "Succeeded". Click it. + * Check to see the result of the runbook at the end of the logic app chain. +### Disable Data Aging from Sentinel +* Go to Sentinel -> (The name of your Sentinel instance) -> Incidents (under Threat Management) -> Create Incident + * Title: + * Cvlt Alert + * Description (Where "< client name >" is the name of the client that you would like to disable data aging on): + * Client < client name > Compromised + * Severity: + * Medium + * Status: + * New + * Click "Create" +* Wait 5-10 minutes for it to run +* Check if it ran: + * Go to Logic Apps -> Commvault-Logic-App + * In the middle of the screen is a table with the column headers Status, Start Time, etc. + * Sort the rows by start time by clicking the "Start Time" column header + * The latest run should say "Succeeded". Click it. + * Check to see the result of the runbook at the end of the logic app chain. \ No newline at end of file diff --git a/Solutions/Commvault Security IQ/ReleaseNotes.md b/Solutions/Commvault Security IQ/ReleaseNotes.md new file mode 100644 index 00000000000..66c42b017a6 --- /dev/null +++ b/Solutions/Commvault Security IQ/ReleaseNotes.md @@ -0,0 +1,3 @@ +| **Version** | **Date Modified (DD-MM-YYYY)** | **Change History** | +|-------------|--------------------------------|---------------------------------------------| +| 3.0.0 | 21-08-2023 | Initial solution release| diff --git a/Solutions/Commvault Security IQ/SolutionMetadata.json b/Solutions/Commvault Security IQ/SolutionMetadata.json new file mode 100644 index 00000000000..f5a5f12266d --- /dev/null +++ b/Solutions/Commvault Security IQ/SolutionMetadata.json @@ -0,0 +1,15 @@ +{ + "publisherId": "commvaultsecurityiq", + "offerId": "azure-sentinel-solution-commvaultsecurityiq", + "firstPublishDate": "2023-08-17", + "providers": ["Commvault"], + "categories": { + "domains": ["Security - Automation (SOAR)"] + }, + "support": { + "tier": "Partner", + "name": "Commvault", + "email": "support@commvault.com", + "link": "https://www.commvault.com/support" + } +}