From dcf5e1e5c7edf13864354cb932a4789942492d28 Mon Sep 17 00:00:00 2001 From: Sean Conroy Date: Mon, 9 Sep 2024 09:58:48 +0100 Subject: [PATCH 01/11] Add missing schema --- ...t_unified_advanced_inspection_profile.json | 326 ++++++++ ...t_unified_advanced_malware_protection.json | 371 +++++++++ ...object_unified_advanced_url_filtering.json | 674 +++++++++++++++ ...y_object_unified_intrusion_prevention.json | 207 +++++ .../policy_object_unified_ssl_decryption.json | 785 ++++++++++++++++++ ...object_unified_ssl_decryption_profile.json | 642 ++++++++++++++ 6 files changed, 3005 insertions(+) create mode 100644 gen/models/profile_parcels/policy_object_unified_advanced_inspection_profile.json create mode 100644 gen/models/profile_parcels/policy_object_unified_advanced_malware_protection.json create mode 100644 gen/models/profile_parcels/policy_object_unified_advanced_url_filtering.json create mode 100644 gen/models/profile_parcels/policy_object_unified_intrusion_prevention.json create mode 100644 gen/models/profile_parcels/policy_object_unified_ssl_decryption.json create mode 100644 gen/models/profile_parcels/policy_object_unified_ssl_decryption_profile.json diff --git a/gen/models/profile_parcels/policy_object_unified_advanced_inspection_profile.json b/gen/models/profile_parcels/policy_object_unified_advanced_inspection_profile.json new file mode 100644 index 00000000..49a9ea50 --- /dev/null +++ b/gen/models/profile_parcels/policy_object_unified_advanced_inspection_profile.json @@ -0,0 +1,326 @@ +{ + "request": { + "$schema": "http://json-schema.org/draft/2019-09/schema", + "$id": "https://cisco.com/schema/profileparcel/sdwan/policy-object/unified/advanced-inspection-profile/post/request_schema.json", + "title": "advanced-malware-protection Parcel Schema", + "description": "advanced-malware-protection profile parcel schema for POST request", + "type": "object", + "properties": { + "name": { + "minLength": 1, + "maxLength": 32, + "type": "string", + "pattern": "^[^&<>! \"]+$" + }, + "description": { + "type": "string" + }, + "data": { + "type": "object", + "minProperties": 1, + "description": "requires tlsDecryptionAction and at least one of Intrusion Prevention or URL Filtering or Advanced Malware Protection policies", + "properties": { + "tlsDecryptionAction": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "decrypt", + "neverDecrypt", + "skipDecrypt" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "intrusionPrevention": { + "type": "object", + "properties": { + "refId": { + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string", + "pattern": "[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + }, + "required": [ + "refId" + ], + "additionalProperties": false + }, + "urlFiltering": { + "type": "object", + "properties": { + "refId": { + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string", + "pattern": "[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + }, + "required": [ + "refId" + ], + "additionalProperties": false + }, + "advancedMalwareProtection": { + "type": "object", + "properties": { + "refId": { + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string", + "pattern": "[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + }, + "required": [ + "refId" + ], + "additionalProperties": false + }, + "sslDecryptionProfile": { + "description": "required if tlsDecryptionAction's value is decrypt", + "type": "object", + "properties": { + "refId": { + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string", + "pattern": "[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + }, + "required": [ + "refId" + ], + "additionalProperties": false + } + }, + "anyOf": [ + { + "required": [ + "intrusionPrevention" + ] + }, + { + "required": [ + "urlFiltering" + ] + }, + { + "required": [ + "advancedMalwareProtection" + ] + } + ], + "required": [ + "tlsDecryptionAction" + ], + "additionalProperties": false + }, + "documentation": { + "description": "This is the documentation for POST request schema for advanced-malware-protection profile parcel", + "details-1": "variable name should be present with given format as specified in schema if optionType value is variable", + "details-2": "variable name should not be present if optionType value is NOT variable", + "details-3": "when option Type is global, value should be present with given format/restrictions as specified in schema", + "details-4": "when option Type is default, value should be present with given default value as specified in schema", + "examples": [ + { + "name": "AIP1", + "description": "No Description", + "data": { + "tlsDecryptionAction": { + "optionType": "global", + "value": "decrypt" + }, + "intrusionPrevention": { + "refId": { + "optionType": "global", + "value": "153b8ad7-77b7-40bb-9ad7-3eb618ee3e58" + } + }, + "urlFiltering": { + "refId": { + "optionType": "global", + "value": "8dc7ad7c-caee-4e9a-a04a-d57a5fe73bca" + } + }, + "advancedMalwareProtection": { + "refId": { + "optionType": "global", + "value": "63633ffd-1f4c-4667-bad0-5cac9948cf87" + } + }, + "sslDecryptionProfile": { + "refId": { + "optionType": "global", + "value": "65ea6eed-e500-473e-8b15-bfcd0cb6adb8" + } + } + } + } + ] + } + }, + "required": [ + "name", + "description", + "data" + ], + "not": { + "required": [ + "documentation" + ] + }, + "allOf": [ + { + "if": { + "properties": { + "data": { + "properties": { + "tlsDecryptionAction": { + "properties": { + "value": { + "enum": [ + "decrypt" + ] + } + } + } + }, + "required": [ + "tlsDecryptionAction" + ] + } + } + }, + "then": { + "properties": { + "data": { + "required": [ + "tlsDecryptionAction", + "sslDecryptionProfile" + ] + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "sslDecryptionProfile": { + "properties": { + "refId": { + "properties": { + "optionType": { + "enum": [ + "global" + ] + } + } + } + } + } + }, + "required": [ + "sslDecryptionProfile" + ] + } + } + }, + "then": { + "properties": { + "data": { + "properties": { + "tlsDecryptionAction": { + "properties": { + "value": { + "enum": [ + "decrypt" + ] + } + } + } + }, + "required": [ + "sslDecryptionProfile" + ] + } + } + } + } + ], + "additionalProperties": false + } +} \ No newline at end of file diff --git a/gen/models/profile_parcels/policy_object_unified_advanced_malware_protection.json b/gen/models/profile_parcels/policy_object_unified_advanced_malware_protection.json new file mode 100644 index 00000000..9270bd01 --- /dev/null +++ b/gen/models/profile_parcels/policy_object_unified_advanced_malware_protection.json @@ -0,0 +1,371 @@ +{ + "request": { + "$schema": "http://json-schema.org/draft/2019-09/schema", + "$id": "https://cisco.com/schema/profileparcel/sdwan/policy-object/unified/advanced-malware-protection/post/request_schema.json", + "title": "advanced-malware-protection Parcel Schema", + "description": "advanced-malware-protection profile parcel schema for POST request", + "type": "object", + "properties": { + "name": { + "minLength": 1, + "maxLength": 32, + "pattern": "^[^&<>! \"]+$", + "type": "string" + }, + "description": { + "type": "string" + }, + "data": { + "type": "object", + "minProperties": 1, + "properties": { + "matchAllVpn": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "const": true + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "fileReputationCloudServer": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "nam", + "eur", + "apjc" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "fileReputationEstServer": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "nam", + "eur", + "apjc" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "fileReputationAlert": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "critical", + "warning", + "info" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "fileAnalysisEnabled": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "boolean" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "fileAnalysisCloudServer": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "nam", + "eur" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "fileAnalysisFileTypes": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "array", + "uniqueItems": true, + "minItems": 1, + "items": { + "type": "string" + } + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "fileAnalysisAlert": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "critical", + "warning", + "info" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + } + }, + "required": [ + "matchAllVpn", + "fileReputationCloudServer", + "fileReputationEstServer", + "fileReputationAlert", + "fileAnalysisEnabled" + ], + "additionalProperties": false + }, + "documentation": { + "description": "This is the documentation for POST request schema for advanced-malware-protection profile parcel", + "details-1": "variable name should be present with given format as specified in schema if optionType value is variable", + "details-2": "variable name should not be present if optionType value is NOT variable", + "details-3": "when option Type is global, value should be present with given format/restrictions as specified in schema", + "details-4": "when option Type is default, value should be present with given default value as specified in schema", + "examples": [ + { + "name": "AMP1", + "description": "advancedMalwareProtection", + "data": { + "matchAllVpn": { + "optionType": "global", + "value": true + }, + "fileReputationCloudServer": { + "optionType": "global", + "value": "nam" + }, + "fileReputationEstServer": { + "optionType": "global", + "value": "nam" + }, + "fileReputationAlert": { + "optionType": "global", + "value": "critical" + }, + "fileAnalysisCloudServer": { + "optionType": "global", + "value": "nam" + }, + "fileAnalysisFileTypes": { + "optionType": "global", + "value": [ + "pdf", + "jpg" + ] + }, + "fileAnalysisAlert": { + "optionType": "global", + "value": "critical" + }, + "fileAnalysisEnabled": { + "optionType": "global", + "value": true + } + } + }, + { + "name": "AMP1", + "description": "advancedMalwareProtection", + "data": { + "matchAllVpn": { + "optionType": "global", + "value": true + }, + "fileReputationCloudServer": { + "optionType": "global", + "value": "nam" + }, + "fileReputationEstServer": { + "optionType": "global", + "value": "nam" + }, + "fileReputationAlert": { + "optionType": "global", + "value": "critical" + }, + "fileAnalysisEnabled": { + "optionType": "global", + "value": false + } + } + } + ] + } + }, + "required": [ + "name", + "description", + "data" + ], + "not": { + "required": [ + "documentation" + ] + }, + "allOf": [ + { + "if": { + "properties": { + "data": { + "properties": { + "fileAnalysisEnabled": { + "properties": { + "value": { + "enum": [ + true + ] + } + } + } + } + } + } + }, + "then": { + "properties": { + "data": { + "required": [ + "fileAnalysisCloudServer", + "fileAnalysisFileTypes", + "fileAnalysisAlert" + ] + } + } + }, + "else": { + "properties": { + "data": { + "not": { + "required": [ + "fileAnalysisCloudServer", + "fileAnalysisFileTypes", + "fileAnalysisAlert" + ] + } + } + } + } + } + ], + "additionalProperties": false + } +} \ No newline at end of file diff --git a/gen/models/profile_parcels/policy_object_unified_advanced_url_filtering.json b/gen/models/profile_parcels/policy_object_unified_advanced_url_filtering.json new file mode 100644 index 00000000..de847f71 --- /dev/null +++ b/gen/models/profile_parcels/policy_object_unified_advanced_url_filtering.json @@ -0,0 +1,674 @@ +{ + "request": { + "$schema": "http://json-schema.org/draft/2019-09/schema", + "$id": "https://cisco.com/schema/profileparcel/sdwan/policy-object/unified/url-filtering/post/request_schema.json", + "title": "url-filtering Parcel Schema", + "description": "url-filtering profile parcel schema for POST request", + "type": "object", + "properties": { + "name": { + "type": "string", + "pattern": "^[^&<>! \"]+$", + "minLength": 1, + "maxLength": 32 + }, + "description": { + "type": "string" + }, + "data": { + "type": "object", + "minProperties": 1, + "properties": { + "webCategoriesAction": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "block", + "allow" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "webCategories": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "array", + "items": { + "type": "string", + "enum": [ + "abortion", + "abused-drugs", + "adult-and-pornography", + "alcohol-and-tobacco", + "auctions", + "bot-nets", + "business-and-economy", + "cdns", + "cheating", + "computer-and-internet-info", + "computer-and-internet-security", + "confirmed-spam-sources", + "cult-and-occult", + "dating", + "dead-sites", + "dynamic-content", + "educational-institutions", + "entertainment-and-arts", + "fashion-and-beauty", + "financial-services", + "gambling", + "games", + "government", + "gross", + "hacking", + "hate-and-racism", + "health-and-medicine", + "home", + "hunting-and-fishing", + "illegal", + "image-and-video-search", + "individual-stock-advice-and-tools", + "internet-communications", + "internet-portals", + "job-search", + "keyloggers-and-monitoring", + "kids", + "legal", + "local-information", + "malware-sites", + "marijuana", + "military", + "motor-vehicles", + "music", + "news-and-media", + "nudity", + "online-greeting-cards", + "online-personal-storage", + "open-http-proxies", + "p2p", + "parked-sites", + "pay-to-surf", + "personal-sites-and-blogs", + "philosophy-and-political-advocacy", + "phishing-and-other-frauds", + "private-ip-addresses", + "proxy-avoid-and-anonymizers", + "questionable", + "real-estate", + "recreation-and-hobbies", + "reference-and-research", + "religion", + "search-engines", + "sex-education", + "shareware-and-freeware", + "shopping", + "social-network", + "society", + "spam-urls", + "sports", + "spyware-and-adware", + "streaming-media", + "swimsuits-and-intimate-apparel", + "training-and-tools", + "translation", + "travel", + "uncategorized", + "unconfirmed-spam-sources", + "violence", + "weapons", + "web-advertisements", + "web-based-email", + "web-hosting" + ] + } + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "webReputation": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "high-risk", + "low-risk", + "moderate-risk", + "suspicious", + "trustworthy" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "urlAllowedList": { + "description": "", + "type": "object", + "properties": { + "refId": { + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string", + "pattern": "[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + } + }, + "urlBlockedList": { + "description": "", + "type": "object", + "properties": { + "refId": { + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string", + "pattern": "[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + } + }, + "blockPageAction": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "text", + "redirect-url" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "blockPageContents": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "redirectUrl": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string", + "pattern": "^(http:\/\/www\\.|https:\/\/www\\.|http:\/\/|https:\/\/)?[a-z0-9]+([\\-\\.]{1}[a-z0-9]+)*\\.[a-z]{2,5}(:[0-9]{1,5})?(\/.*)?$" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "enableAlerts": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "boolean" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "alerts": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "array", + "items": { + "type": "string", + "enum": [ + "blacklist", + "whitelist", + "categories-reputation" + ] + } + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + } + }, + "required": [ + "webCategoriesAction", + "webReputation", + "blockPageAction", + "enableAlerts" + ], + "additionalProperties": false + } + }, + "documentation": { + "description": "This is the documentation for POST request schema for url-filtering profile parcel", + "details-1": "variable name should be present with given format as specified in schema if optionType value is variable", + "details-2": "variable name should not be present if optionType value is NOT variable", + "details-3": "when option Type is global, value should be present with given format/restrictions as specified in schema", + "details-4": "when option Type is default, value should be present with given default value as specified in schema", + "examples": [ + { + "data": { + "webCategoriesAction": { + "optionType": "global", + "value": "block" + }, + "webCategories": { + "optionType": "global", + "value": "confirmed-spam-sources" + }, + "webReputation": { + "optionType": "global", + "value": "suspicious" + }, + "urlAllowedList": { + "optionType": "global", + "value": "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + }, + "urlBlockedList": { + "optionType": "global", + "value": "258d8410-f741-4776-9a4f-300ead0948cc" + }, + "blockPageAction": { + "optionType": "global", + "value": "text" + }, + "blockPageContents": { + "optionType": "global", + "value": "Access to the requested page has been denied. Please contact your Network Administrator" + }, + "enableAlerts": { + "optionType": "global", + "value": true + }, + "alerts": { + "optionType": "global", + "value": "blacklist" + } + }, + "name": "security-urlfilteringParcelGlobalDefault" + } + ] + }, + "required": [ + "data", + "name" + ], + "not": { + "required": [ + "documentation" + ] + }, + "anyOf": [ + { + "if": { + "properties": { + "data": { + "properties": { + "webCategoriesAction": { + "properties": { + "value": { + "enum": [ + "accept" + ] + } + } + } + }, + "required": [ + "webCategoriesAction" + ] + } + } + }, + "then": { + "properties": { + "data": { + "required": [ + "webCategories" + ] + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "enableAlerts": { + "properties": { + "value": { + "boolean": [ + true + ] + } + } + } + }, + "required": [ + "enableAlerts" + ] + } + } + }, + "then": { + "properties": { + "data": { + "required": [ + "alerts" + ] + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "enableAlerts": { + "properties": { + "value": { + "boolean": [ + false + ] + } + } + } + }, + "required": [ + "enableAlerts" + ] + } + } + }, + "then": { + "properties": { + "data": { + "not": { + "required": [ + "alerts" + ] + } + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "blockPageAction": { + "properties": { + "value": { + "enum": [ + "text" + ] + } + } + } + }, + "required": [ + "blockPageAction" + ] + } + } + }, + "then": { + "properties": { + "data": { + "required": [ + "blockPageContents" + ] + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "blockPageAction": { + "properties": { + "value": { + "enum": [ + "redirectUrl" + ] + } + } + } + }, + "required": [ + "blockPageAction" + ] + } + } + }, + "then": { + "properties": { + "data": { + "not": { + "required": [ + "blockPageContents" + ] + } + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "blockPageAction": { + "properties": { + "value": { + "enum": [ + "redirect-url" + ] + } + } + } + }, + "required": [ + "blockPageAction" + ] + } + } + }, + "then": { + "properties": { + "data": { + "required": [ + "redirectUrl" + ] + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "blockPageAction": { + "properties": { + "value": { + "enum": [ + "text" + ] + } + } + } + }, + "required": [ + "blockPageAction" + ] + } + } + }, + "then": { + "properties": { + "data": { + "not": { + "required": [ + "redirectUrl" + ] + } + } + } + } + } + ], + "additionalProperties": false + } +} \ No newline at end of file diff --git a/gen/models/profile_parcels/policy_object_unified_intrusion_prevention.json b/gen/models/profile_parcels/policy_object_unified_intrusion_prevention.json new file mode 100644 index 00000000..246bfc69 --- /dev/null +++ b/gen/models/profile_parcels/policy_object_unified_intrusion_prevention.json @@ -0,0 +1,207 @@ +{ + "request": { + "$schema": "http://json-schema.org/draft/2019-09/schema", + "$id": "https://cisco.com/schema/profileparcel/sdwan/policy-object/unified/intrusion-prevention/post/request_schema.json", + "title": "Intrusion Prevention Parcel Schema", + "description": "Intrusion Prevention profile parcel schema for POST request", + "type": "object", + "properties": { + "name": { + "type": "string", + "pattern": "^[^&<>! \"]+$", + "minLength": 1, + "maxLength": 32 + }, + "description": { + "type": "string" + }, + "data": { + "type": "object", + "minProperties": 1, + "properties": { + "signatureSet": { + "description": "Can be one of the enum value", + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "balanced", + "connectivity", + "security" + ], + "type": "string", + "default": "balanced" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + }, + "inspectionMode": { + "description": "Can be one of the enum value", + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "detection", + "protection" + ], + "type": "string", + "default": "detection" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + }, + "signatureAllowedList": { + "description": "Valid UUID", + "type": "object", + "properties": { + "refId": { + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string", + "pattern": "[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + } + }, + "logLevel": { + "description": "Can be one of the enum value", + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "emergency", + "alert", + "critical", + "error", + "warning", + "notice", + "info", + "debug" + ], + "type": "string", + "default": "error" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + }, + "customSignature": { + "description": "Can be one of the enum value", + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "boolean", + "default": false + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + }, + "required": [ + "signatureSet", + "inspectionMode", + "logLevel" + ], + "additionalProperties": false + }, + "documentation": { + "description": "This is the documentation for POST request schema for Intrusion Prevention profile parcel", + "details-1": "variable name should be present with given format as specified in schema if optionType value is variable", + "details-2": "variable name should not be present if optionType value is NOT variable", + "details-3": "when option Type is global, value should be present with given format/restrictions as specified in schema", + "details-4": "when option Type is default, value should be present with given default value as specified in schema", + "examples": [ + { + "data": { + "signatureSet": { + "optionType": "global", + "value": "balanced" + }, + "inspectionMode": { + "optionType": "global", + "value": "detection" + }, + "signatureAllowedList": { + "refId": { + "optionType": "global", + "value": "f2add913-a9ed-4aef-a3b8-760d655ab029" + } + }, + "logLevel": { + "optionType": "global", + "value": "error" + }, + "customSignature": { + "optionType": "global", + "value": false + } + }, + "name": "Intrusion Prevention Parcel" + } + ] + } + }, + "required": [ + "name", + "data" + ], + "not": { + "required": [ + "documentation" + ] + }, + "additionalProperties": false + } +} \ No newline at end of file diff --git a/gen/models/profile_parcels/policy_object_unified_ssl_decryption.json b/gen/models/profile_parcels/policy_object_unified_ssl_decryption.json new file mode 100644 index 00000000..fa042eb2 --- /dev/null +++ b/gen/models/profile_parcels/policy_object_unified_ssl_decryption.json @@ -0,0 +1,785 @@ +{ + "request": { + "$schema": "http://json-schema.org/draft/2019-09/schema", + "$id": "https://cisco.com/schema/profileparcel/sdwan/policy-object/unified/ssl-decryption/post/request_schema.json", + "title": "ssl-decryption Parcel Schema", + "description": "ssl-decryption profile parcel schema for POST request", + "type": "object", + "properties": { + "name": { + "maxLength": 32, + "type": "string", + "pattern": "^[^&<>! \"]+$", + "minLength": 1 + }, + "description": { + "description": "Will be auto generated", + "type": "string" + }, + "data": { + "type": "object", + "minProperties": 1, + "properties": { + "sslEnable": { + "description": "If false, no other fields should be provided, if true all fields should be provided", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "boolean" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "expiredCertificate": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "decrypt", + "drop" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "untrustedCertificate": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "decrypt", + "drop" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "certificateRevocationStatus": { + "description": "If value is none unknown status not required, if value is ocsp then unknown status is required", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "ocsp", + "none" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "unknownStatus": { + "description": "Only required if certificateRevocationStatus is oscp, if value is none then field shouldn't be here", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "decrypt", + "drop" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "unsupportedProtocolVersions": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "no-decrypt", + "drop" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "unsupportedCipherSuites": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "no-decrypt", + "drop" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "failureMode": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "close", + "open" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "caCertBundle": { + "description": "If default is false have to provide file name and bundleString", + "oneOf": [ + { + "properties": { + "default": { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "boolean" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + }, + "required": [ + "default" + ], + "additionalProperties": false + }, + { + "properties": { + "default": { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "boolean" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + }, + "fileName": { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + }, + "bundleString": { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + }, + "required": [ + "default", + "fileName", + "bundleString" + ], + "additionalProperties": false + } + ] + }, + "keyModulus": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "1024", + "2048", + "4096" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "eckeyType": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "P256", + "P384", + "P521" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "certificateLifetime": { + "description": "If you have vManage as CA or vManage as intermediate CA, this value should be 1", + "details-1": "If another value is entered it will not be used", + "details-2": "If you have Enterprise CA value should be greater than 0", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "minTlsVer": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "TLSv1", + "TLSv1.1", + "TLSv1.2" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "caTpLabel": { + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "PROXY-SIGNING-CA" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + } + }, + "required": [ + "sslEnable" + ], + "additionalProperties": false + }, + "documentation": { + "description": "This is the documentation for POST request schema for ssl-decryption profile parcel", + "details-1": "variable name should be present with given format as specified in schema if optionType value is variable", + "details-2": "variable name should not be present if optionType value is NOT variable", + "details-3": "when option Type is global, value should be present with given format/restrictions as specified in schema", + "details-4": "when option Type is default, value should be present with given default value as specified in schema", + "examples": [ + { + "data": { + "sslEnable": { + "optionType": "global", + "value": true + }, + "expiredCertificate": { + "optionType": "global", + "value": "drop" + }, + "untrustedCertificate": { + "optionType": "global", + "value": "drop" + }, + "certificateRevocationStatus": { + "optionType": "global", + "value": "ocsp" + }, + "unknownStatus": { + "optionType": "global", + "value": "decrypt" + }, + "unsupportedProtocolVersions": { + "optionType": "global", + "value": "no-decrypt" + }, + "unsupportedCipherSuites": { + "optionType": "global", + "value": "drop" + }, + "failureMode": { + "optionType": "global", + "value": "close" + }, + "caCertBundle": { + "default": { + "optionType": "global", + "value": false + }, + "fileName": { + "optionType": "global", + "value": "dummy.pem" + }, + "bundleString": { + "optionType": "global", + "value": "testString" + } + }, + "keyModulus": { + "optionType": "global", + "value": "2048" + }, + "eckeyType": { + "optionType": "global", + "value": "P384" + }, + "certificateLifetime": { + "optionType": "global", + "value": "1" + }, + "minTlsVer": { + "optionType": "global", + "value": "TLSv1.2" + }, + "caTpLabel": { + "optionType": "global", + "value": "PROXY-SIGNING-CA" + } + }, + "name": "ssl-decryptionParcel", + "description": "TLS/SSL Proxy Policy Definition" + } + ] + } + }, + "required": [ + "name", + "description", + "data" + ], + "not": { + "required": [ + "documentation" + ] + }, + "allOf": [ + { + "if": { + "properties": { + "data": { + "properties": { + "sslEnable": { + "properties": { + "value": { + "const": true + } + } + } + }, + "required": [ + "sslEnable" + ] + } + } + }, + "then": { + "properties": { + "data": { + "required": [ + "sslEnable", + "expiredCertificate", + "untrustedCertificate", + "certificateRevocationStatus", + "unsupportedProtocolVersions", + "unsupportedCipherSuites", + "failureMode", + "caCertBundle", + "keyModulus", + "eckeyType", + "certificateLifetime", + "minTlsVer", + "caTpLabel" + ] + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "sslEnable": { + "properties": { + "value": { + "const": false + } + } + } + }, + "required": [ + "sslEnable" + ] + } + } + }, + "then": { + "properties": { + "data": { + "not": { + "required": [ + "sslEnable", + "expiredCertificate", + "untrustedCertificate", + "certificateRevocationStatus", + "unsupportedProtocolVersions", + "unsupportedCipherSuites", + "failureMode", + "caCertBundle", + "keyModulus", + "eckeyType", + "certificateLifetime", + "minTlsVer", + "caTpLabel" + ] + } + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "certificateRevocationStatus": { + "properties": { + "value": { + "enum": [ + "ocsp" + ] + } + } + } + }, + "required": [ + "certificateRevocationStatus" + ] + } + } + }, + "then": { + "properties": { + "data": { + "required": [ + "unknownStatus" + ] + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "certificateRevocationStatus": { + "properties": { + "value": { + "enum": [ + "none" + ] + } + } + } + }, + "required": [ + "certificateRevocationStatus" + ] + } + } + }, + "then": { + "properties": { + "data": { + "not": { + "required": [ + "unknownStatus" + ] + } + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "caCertBundle": { + "properties": { + "default": { + "properties": { + "value": { + "const": true + } + } + } + } + } + }, + "required": [ + "certificateRevocationStatus" + ] + } + } + }, + "then": { + "properties": { + "data": { + "properties": { + "caCertBundle": { + "not": { + "required": [ + "fileName", + "bundleString" + ] + } + } + } + } + } + } + }, + { + "if": { + "properties": { + "data": { + "properties": { + "caCertBundle": { + "properties": { + "default": { + "properties": { + "value": { + "const": false + } + } + } + } + } + }, + "required": [ + "certificateRevocationStatus" + ] + } + } + }, + "then": { + "properties": { + "data": { + "properties": { + "caCertBundle": { + "required": [ + "default", + "fileName", + "bundleString" + ] + } + } + } + } + } + } + ], + "additionalProperties": false + } +} \ No newline at end of file diff --git a/gen/models/profile_parcels/policy_object_unified_ssl_decryption_profile.json b/gen/models/profile_parcels/policy_object_unified_ssl_decryption_profile.json new file mode 100644 index 00000000..25990e43 --- /dev/null +++ b/gen/models/profile_parcels/policy_object_unified_ssl_decryption_profile.json @@ -0,0 +1,642 @@ +{ + "request": { + "$schema": "http://json-schema.org/draft/2019-09/schema", + "$id": "https://cisco.com/schema/profileparcel/sdwan/policy-object/unified/ssl-decryption-profile/post/request_schema.json", + "title": "ssl-decryption-profile Parcel Schema", + "description": "ssl-decryption-profile profile parcel schema for POST request", + "type": "object", + "properties": { + "name": { + "type": "string", + "pattern": "^[^&<>! \"]+$", + "minLength": 1, + "maxLength": 32 + }, + "description": { + "type": "string" + }, + "data": { + "type": "object", + "minProperties": 1, + "properties": { + "decryptCategories": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "array", + "items": { + "type": "string", + "enum": [ + "abortion", + "abused-drugs", + "adult-and-pornography", + "alcohol-and-tobacco", + "auctions", + "bot-nets", + "business-and-economy", + "cdns", + "cheating", + "computer-and-internet-info", + "computer-and-internet-security", + "confirmed-spam-sources", + "cult-and-occult", + "dating", + "dead-sites", + "dynamic-content", + "educational-institutions", + "entertainment-and-arts", + "fashion-and-beauty", + "financial-services", + "gambling", + "games", + "government", + "gross", + "hacking", + "hate-and-racism", + "health-and-medicine", + "home", + "hunting-and-fishing", + "illegal", + "image-and-video-search", + "individual-stock-advice-and-tools", + "internet-communications", + "internet-portals", + "job-search", + "keyloggers-and-monitoring", + "kids", + "legal", + "local-information", + "malware-sites", + "marijuana", + "military", + "motor-vehicles", + "music", + "news-and-media", + "nudity", + "online-greeting-cards", + "online-personal-storage", + "open-http-proxies", + "p2p", + "parked-sites", + "pay-to-surf", + "personal-sites-and-blogs", + "philosophy-and-political-advocacy", + "phishing-and-other-frauds", + "private-ip-addresses", + "proxy-avoid-and-anonymizers", + "questionable", + "real-estate", + "recreation-and-hobbies", + "reference-and-research", + "religion", + "search-engines", + "sex-education", + "shareware-and-freeware", + "shopping", + "social-network", + "society", + "spam-urls", + "sports", + "spyware-and-adware", + "streaming-media", + "swimsuits-and-intimate-apparel", + "training-and-tools", + "translation", + "travel", + "uncategorized", + "unconfirmed-spam-sources", + "violence", + "weapons", + "web-advertisements", + "web-based-email", + "web-hosting" + ] + } + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "neverDecryptCategories": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "array", + "items": { + "type": "string", + "enum": [ + "abortion", + "abused-drugs", + "adult-and-pornography", + "alcohol-and-tobacco", + "auctions", + "bot-nets", + "business-and-economy", + "cdns", + "cheating", + "computer-and-internet-info", + "computer-and-internet-security", + "confirmed-spam-sources", + "cult-and-occult", + "dating", + "dead-sites", + "dynamic-content", + "educational-institutions", + "entertainment-and-arts", + "fashion-and-beauty", + "financial-services", + "gambling", + "games", + "government", + "gross", + "hacking", + "hate-and-racism", + "health-and-medicine", + "home", + "hunting-and-fishing", + "illegal", + "image-and-video-search", + "individual-stock-advice-and-tools", + "internet-communications", + "internet-portals", + "job-search", + "keyloggers-and-monitoring", + "kids", + "legal", + "local-information", + "malware-sites", + "marijuana", + "military", + "motor-vehicles", + "music", + "news-and-media", + "nudity", + "online-greeting-cards", + "online-personal-storage", + "open-http-proxies", + "p2p", + "parked-sites", + "pay-to-surf", + "personal-sites-and-blogs", + "philosophy-and-political-advocacy", + "phishing-and-other-frauds", + "private-ip-addresses", + "proxy-avoid-and-anonymizers", + "questionable", + "real-estate", + "recreation-and-hobbies", + "reference-and-research", + "religion", + "search-engines", + "sex-education", + "shareware-and-freeware", + "shopping", + "social-network", + "society", + "spam-urls", + "sports", + "spyware-and-adware", + "streaming-media", + "swimsuits-and-intimate-apparel", + "training-and-tools", + "translation", + "travel", + "uncategorized", + "unconfirmed-spam-sources", + "violence", + "weapons", + "web-advertisements", + "web-based-email", + "web-hosting" + ] + } + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "skipDecryptCategories": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "array", + "items": { + "type": "string", + "enum": [ + "abortion", + "abused-drugs", + "adult-and-pornography", + "alcohol-and-tobacco", + "auctions", + "bot-nets", + "business-and-economy", + "cdns", + "cheating", + "computer-and-internet-info", + "computer-and-internet-security", + "confirmed-spam-sources", + "cult-and-occult", + "dating", + "dead-sites", + "dynamic-content", + "educational-institutions", + "entertainment-and-arts", + "fashion-and-beauty", + "financial-services", + "gambling", + "games", + "government", + "gross", + "hacking", + "hate-and-racism", + "health-and-medicine", + "home", + "hunting-and-fishing", + "illegal", + "image-and-video-search", + "individual-stock-advice-and-tools", + "internet-communications", + "internet-portals", + "job-search", + "keyloggers-and-monitoring", + "kids", + "legal", + "local-information", + "malware-sites", + "marijuana", + "military", + "motor-vehicles", + "music", + "news-and-media", + "nudity", + "online-greeting-cards", + "online-personal-storage", + "open-http-proxies", + "p2p", + "parked-sites", + "pay-to-surf", + "personal-sites-and-blogs", + "philosophy-and-political-advocacy", + "phishing-and-other-frauds", + "private-ip-addresses", + "proxy-avoid-and-anonymizers", + "questionable", + "real-estate", + "recreation-and-hobbies", + "reference-and-research", + "religion", + "search-engines", + "sex-education", + "shareware-and-freeware", + "shopping", + "social-network", + "society", + "spam-urls", + "sports", + "spyware-and-adware", + "streaming-media", + "swimsuits-and-intimate-apparel", + "training-and-tools", + "translation", + "travel", + "uncategorized", + "unconfirmed-spam-sources", + "violence", + "weapons", + "web-advertisements", + "web-based-email", + "web-hosting" + ] + } + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "reputation": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "boolean" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "decryptThreshold": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "high-risk", + "low-risk", + "moderate-risk", + "suspicious", + "trustworthy" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "skipDecryptThreshold": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "enum": [ + "high-risk", + "low-risk", + "moderate-risk", + "suspicious", + "trustworthy" + ], + "type": "string" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "failDecrypt": { + "description": "", + "type": "object", + "oneOf": [ + { + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "boolean" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + ] + }, + "urlAllowedList": { + "description": "", + "type": "object", + "properties": { + "refId": { + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string", + "pattern": "[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + } + }, + "urlBlockedList": { + "description": "", + "type": "object", + "properties": { + "refId": { + "type": "object", + "properties": { + "optionType": { + "type": "string", + "enum": [ + "global" + ] + }, + "value": { + "type": "string", + "pattern": "[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}" + } + }, + "required": [ + "optionType", + "value" + ], + "additionalProperties": false + } + } + } + }, + "required": [ + "decryptCategories", + "neverDecryptCategories", + "reputation", + "failDecrypt" + ], + "additionalProperties": false + }, + "documentation": { + "description": "This is the documentation for POST request schema for ssl-decryption-profile profile parcel", + "details-1": "variable name should be present with given format as specified in schema if optionType value is variable", + "details-2": "variable name should not be present if optionType value is NOT variable", + "details-3": "when option Type is global, value should be present with given format/restrictions as specified in schema", + "details-4": "when option Type is default, value should be present with given default value as specified in schema", + "examples": [ + { + "data": { + "decryptCategories": { + "optionType": "global", + "value": [ + "alcohol-and-tobacco" + ] + }, + "neverDecryptCategories": { + "optionType": "global", + "value": [ + "abortion" + ] + }, + "skipDecryptCategories": { + "optionType": "global", + "value": [ + "auctions" + ] + }, + "reputation": { + "optionType": "global", + "value": true + }, + "decryptThreshold": { + "optionType": "global", + "value": "moderate-risk" + }, + "skipDecryptThreshold": { + "optionType": "global", + "value": "moderate-risk" + }, + "failDecrypt": { + "optionType": "global", + "value": true + }, + "urlAllowedList": { + "optionType": "global", + "value": "da9094b1-40fa-4eb1-bcbd-0ab79be8cae0" + }, + "urlBlockedList": { + "optionType": "global", + "value": "1f2a32f5-3251-40b1-b45f-61a2c44320cc" + } + }, + "name": "ssl-decryption-profileParcelGlobalDefault" + } + ] + } + }, + "required": [ + "data", + "description", + "name" + ], + "not": { + "required": [ + "documentation" + ] + }, + "allOf": [ + { + "if": { + "properties": { + "data": { + "properties": { + "reputation": { + "properties": { + "value": { + "enum": [ + true + ] + } + } + } + }, + "required": [ + "reputation" + ] + } + } + }, + "then": { + "properties": { + "data": { + "required": [ + "decryptThreshold" + ] + } + } + }, + "else": { + "properties": { + "data": { + "not": { + "required": [ + "decryptThreshold" + ] + } + } + } + } + } + ], + "additionalProperties": false + } +} \ No newline at end of file From eb02dff05c4ebee4db2a0caa87558b7753c103ef Mon Sep 17 00:00:00 2001 From: Sean Conroy Date: Mon, 9 Sep 2024 10:06:25 +0100 Subject: [PATCH 02/11] Add policy object unified advanced malware protection resource and data source --- CHANGELOG.md | 1 + ...ect_unified_advanced_malware_protection.md | 42 +++ docs/guides/changelog.md | 1 + ...ect_unified_advanced_malware_protection.md | 64 ++++ .../data-source.tf | 4 + .../import.sh | 1 + .../resource.tf | 13 + ...t_unified_advanced_malware_protection.yaml | 45 +++ ...ect_unified_advanced_malware_protection.go | 155 +++++++++ ...nified_advanced_malware_protection_test.go | 93 ++++++ ...ect_unified_advanced_malware_protection.go | 314 ++++++++++++++++++ internal/provider/provider.go | 2 + ...ect_unified_advanced_malware_protection.go | 290 ++++++++++++++++ ...nified_advanced_malware_protection_test.go | 91 +++++ templates/guides/changelog.md.tmpl | 1 + 15 files changed, 1117 insertions(+) create mode 100644 docs/data-sources/policy_object_unified_advanced_malware_protection.md create mode 100644 docs/resources/policy_object_unified_advanced_malware_protection.md create mode 100644 examples/data-sources/sdwan_policy_object_unified_advanced_malware_protection/data-source.tf create mode 100644 examples/resources/sdwan_policy_object_unified_advanced_malware_protection/import.sh create mode 100644 examples/resources/sdwan_policy_object_unified_advanced_malware_protection/resource.tf create mode 100644 gen/definitions/profile_parcels/policy_object_unified_advanced_malware_protection.yaml create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection.go create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection_test.go create mode 100644 internal/provider/model_sdwan_policy_object_unified_advanced_malware_protection.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection_test.go diff --git a/CHANGELOG.md b/CHANGELOG.md index 524fe663..0994dc41 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,7 @@ - Add `sdwan_policy_object_application_list` resource and data source - Add `sdwan_policy_object_sla_class_list` resource and data source +- Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source ## 0.4.1 diff --git a/docs/data-sources/policy_object_unified_advanced_malware_protection.md b/docs/data-sources/policy_object_unified_advanced_malware_protection.md new file mode 100644 index 00000000..7488853b --- /dev/null +++ b/docs/data-sources/policy_object_unified_advanced_malware_protection.md @@ -0,0 +1,42 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_advanced_malware_protection Data Source - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This data source can read the Policy Object Unified Advanced Malware Protection Policy_object. +--- + +# sdwan_policy_object_unified_advanced_malware_protection (Data Source) + +This data source can read the Policy Object Unified Advanced Malware Protection Policy_object. + +## Example Usage + +```terraform +data "sdwan_policy_object_unified_advanced_malware_protection" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} +``` + + +## Schema + +### Required + +- `feature_profile_id` (String) Feature Profile ID +- `id` (String) The id of the Policy_object + +### Read-Only + +- `alert_log_level` (String) +- `amp_cloud_region` (String) +- `amp_cloud_region_est_server` (String) +- `description` (String) The description of the Policy_object +- `file_analysis` (Boolean) +- `file_analysis_alert_log_level` (String) +- `file_analysis_cloud_region` (String) +- `file_analysis_file_types` (Set of String) +- `match_all_vpn` (Boolean) +- `name` (String) The name of the Policy_object +- `version` (Number) The version of the Policy_object diff --git a/docs/guides/changelog.md b/docs/guides/changelog.md index aed0b467..771e8438 100644 --- a/docs/guides/changelog.md +++ b/docs/guides/changelog.md @@ -11,6 +11,7 @@ description: |- - Add `sdwan_policy_object_application_list` resource and data source - Add `sdwan_policy_object_sla_class_list` resource and data source +- Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source ## 0.4.1 diff --git a/docs/resources/policy_object_unified_advanced_malware_protection.md b/docs/resources/policy_object_unified_advanced_malware_protection.md new file mode 100644 index 00000000..9fbbcaa0 --- /dev/null +++ b/docs/resources/policy_object_unified_advanced_malware_protection.md @@ -0,0 +1,64 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_advanced_malware_protection Resource - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This resource can manage a Policy Object Unified Advanced Malware Protection Policy_object. + Minimum SD-WAN Manager version: 20.12.0 +--- + +# sdwan_policy_object_unified_advanced_malware_protection (Resource) + +This resource can manage a Policy Object Unified Advanced Malware Protection Policy_object. + - Minimum SD-WAN Manager version: `20.12.0` + +## Example Usage + +```terraform +resource "sdwan_policy_object_unified_advanced_malware_protection" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + match_all_vpn = true + amp_cloud_region = "nam" + amp_cloud_region_est_server = "nam" + alert_log_level = "critical" + file_analysis = true + file_analysis_cloud_region = "nam" + file_analysis_file_types = ["pdf"] + file_analysis_alert_log_level = "critical" +} +``` + + +## Schema + +### Required + +- `alert_log_level` (String) - Choices: `critical`, `warning`, `info` +- `amp_cloud_region` (String) - Choices: `nam`, `eur`, `apjc` +- `amp_cloud_region_est_server` (String) - Choices: `nam`, `eur`, `apjc` +- `feature_profile_id` (String) Feature Profile ID +- `file_analysis` (Boolean) +- `file_analysis_alert_log_level` (String) - Choices: `critical`, `warning`, `info` +- `file_analysis_cloud_region` (String) - Choices: `nam`, `eur` +- `file_analysis_file_types` (Set of String) +- `match_all_vpn` (Boolean) +- `name` (String) The name of the Policy_object + +### Optional + +- `description` (String) The description of the Policy_object + +### Read-Only + +- `id` (String) The id of the Policy_object +- `version` (Number) The version of the Policy_object + +## Import + +Import is supported using the following syntax: + +```shell +terraform import sdwan_policy_object_unified_advanced_malware_protection.example "f6b2c44c-693c-4763-b010-895aa3d236bd" +``` diff --git a/examples/data-sources/sdwan_policy_object_unified_advanced_malware_protection/data-source.tf b/examples/data-sources/sdwan_policy_object_unified_advanced_malware_protection/data-source.tf new file mode 100644 index 00000000..5392cc8d --- /dev/null +++ b/examples/data-sources/sdwan_policy_object_unified_advanced_malware_protection/data-source.tf @@ -0,0 +1,4 @@ +data "sdwan_policy_object_unified_advanced_malware_protection" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} diff --git a/examples/resources/sdwan_policy_object_unified_advanced_malware_protection/import.sh b/examples/resources/sdwan_policy_object_unified_advanced_malware_protection/import.sh new file mode 100644 index 00000000..7634cbd5 --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_advanced_malware_protection/import.sh @@ -0,0 +1 @@ +terraform import sdwan_policy_object_unified_advanced_malware_protection.example "f6b2c44c-693c-4763-b010-895aa3d236bd" diff --git a/examples/resources/sdwan_policy_object_unified_advanced_malware_protection/resource.tf b/examples/resources/sdwan_policy_object_unified_advanced_malware_protection/resource.tf new file mode 100644 index 00000000..f52ef471 --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_advanced_malware_protection/resource.tf @@ -0,0 +1,13 @@ +resource "sdwan_policy_object_unified_advanced_malware_protection" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + match_all_vpn = true + amp_cloud_region = "nam" + amp_cloud_region_est_server = "nam" + alert_log_level = "critical" + file_analysis = true + file_analysis_cloud_region = "nam" + file_analysis_file_types = ["pdf"] + file_analysis_alert_log_level = "critical" +} diff --git a/gen/definitions/profile_parcels/policy_object_unified_advanced_malware_protection.yaml b/gen/definitions/profile_parcels/policy_object_unified_advanced_malware_protection.yaml new file mode 100644 index 00000000..99b17f3f --- /dev/null +++ b/gen/definitions/profile_parcels/policy_object_unified_advanced_malware_protection.yaml @@ -0,0 +1,45 @@ +--- +name: Policy Object Unified Advanced Malware Protection +rest_endpoint: /v1/feature-profile/sdwan/policy-object/%v/unified/advanced-malware-protection +minimum_version: 20.12.0 +test_tags: [SDWAN_2012] +skip_minimum_test: true +parcel_type: policy_object +attributes: + - tf_name: feature_profile_id + reference: true + type: String + mandatory: true + description: Feature Profile ID + example: f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac + test_value: sdwan_policy_object_feature_profile.test.id + - model_name: matchAllVpn + tf_name: match_all_vpn + example: true + - model_name: fileReputationCloudServer + tf_name: amp_cloud_region + example: nam + - model_name: fileReputationEstServer + tf_name: amp_cloud_region_est_server + example: nam + - model_name: fileReputationAlert + tf_name: alert_log_level + example: critical + - model_name: fileAnalysisEnabled + tf_name: file_analysis + example: true + - model_name: fileAnalysisCloudServer + tf_name: file_analysis_cloud_region + example: nam + - model_name: fileAnalysisFileTypes + tf_name: file_analysis_file_types + example: pdf + - model_name: fileAnalysisAlert + tf_name: file_analysis_alert_log_level + example: critical + +test_prerequisites: | + resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" + } diff --git a/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection.go b/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection.go new file mode 100644 index 00000000..bdac27de --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection.go @@ -0,0 +1,155 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/hashicorp/terraform-plugin-framework/datasource" + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure the implementation satisfies the expected interfaces. +var ( + _ datasource.DataSource = &PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource{} + _ datasource.DataSourceWithConfigure = &PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource{} +) + +func NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource() datasource.DataSource { + return &PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource{} +} + +type PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource struct { + client *sdwan.Client +} + +func (d *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource) Metadata(_ context.Context, req datasource.MetadataRequest, resp *datasource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_advanced_malware_protection" +} + +func (d *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource) Schema(ctx context.Context, req datasource.SchemaRequest, resp *datasource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: "This data source can read the Policy Object Unified Advanced Malware Protection Policy_object.", + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Required: true, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Computed: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Computed: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: "Feature Profile ID", + Required: true, + }, + "match_all_vpn": schema.BoolAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "amp_cloud_region": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "amp_cloud_region_est_server": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "alert_log_level": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "file_analysis": schema.BoolAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "file_analysis_cloud_region": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "file_analysis_file_types": schema.SetAttribute{ + MarkdownDescription: "", + ElementType: types.StringType, + Computed: true, + }, + "file_analysis_alert_log_level": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + }, + } +} + +func (d *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource) Configure(_ context.Context, req datasource.ConfigureRequest, _ *datasource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + d.client = req.ProviderData.(*SdwanProviderData).Client +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (d *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource) Read(ctx context.Context, req datasource.ReadRequest, resp *datasource.ReadResponse) { + var config PolicyObjectUnifiedAdvancedMalwareProtection + + // Read config + diags := req.Config.Get(ctx, &config) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", config.Id.String())) + + res, err := d.client.Get(config.getPath() + "/" + url.QueryEscape(config.Id.ValueString())) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object, got error: %s", err)) + return + } + + config.fromBody(ctx, res) + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", config.Name.ValueString())) + + diags = resp.State.Set(ctx, &config) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read diff --git a/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection_test.go b/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection_test.go new file mode 100644 index 00000000..430083a8 --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection_test.go @@ -0,0 +1,93 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSource +func TestAccDataSourceSdwanPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_malware_protection.test", "match_all_vpn", "true")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_malware_protection.test", "amp_cloud_region", "nam")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_malware_protection.test", "amp_cloud_region_est_server", "nam")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_malware_protection.test", "alert_log_level", "critical")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_malware_protection.test", "file_analysis", "true")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_malware_protection.test", "file_analysis_cloud_region", "nam")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_malware_protection.test", "file_analysis_alert_log_level", "critical")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + { + Config: testAccDataSourceSdwanPolicyObjectUnifiedAdvancedMalwareProtectionPrerequisitesProfileParcelConfig + testAccDataSourceSdwanPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelConfig(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAccDataSource + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccDataSourceSdwanPolicyObjectUnifiedAdvancedMalwareProtectionPrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} + +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSourceConfig +func testAccDataSourceSdwanPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelConfig() string { + config := `resource "sdwan_policy_object_unified_advanced_malware_protection" "test" {` + "\n" + config += ` name = "TF_TEST"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` match_all_vpn = true` + "\n" + config += ` amp_cloud_region = "nam"` + "\n" + config += ` amp_cloud_region_est_server = "nam"` + "\n" + config += ` alert_log_level = "critical"` + "\n" + config += ` file_analysis = true` + "\n" + config += ` file_analysis_cloud_region = "nam"` + "\n" + config += ` file_analysis_file_types = ["pdf"]` + "\n" + config += ` file_analysis_alert_log_level = "critical"` + "\n" + config += `}` + "\n" + + config += ` + data "sdwan_policy_object_unified_advanced_malware_protection" "test" { + id = sdwan_policy_object_unified_advanced_malware_protection.test.id + feature_profile_id = sdwan_policy_object_feature_profile.test.id + } + ` + return config +} + +// End of section. //template:end testAccDataSourceConfig diff --git a/internal/provider/model_sdwan_policy_object_unified_advanced_malware_protection.go b/internal/provider/model_sdwan_policy_object_unified_advanced_malware_protection.go new file mode 100644 index 00000000..3bc71a08 --- /dev/null +++ b/internal/provider/model_sdwan_policy_object_unified_advanced_malware_protection.go @@ -0,0 +1,314 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/CiscoDevNet/terraform-provider-sdwan/internal/provider/helpers" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/tidwall/gjson" + "github.com/tidwall/sjson" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin types +type PolicyObjectUnifiedAdvancedMalwareProtection struct { + Id types.String `tfsdk:"id"` + Version types.Int64 `tfsdk:"version"` + Name types.String `tfsdk:"name"` + Description types.String `tfsdk:"description"` + FeatureProfileId types.String `tfsdk:"feature_profile_id"` + MatchAllVpn types.Bool `tfsdk:"match_all_vpn"` + AmpCloudRegion types.String `tfsdk:"amp_cloud_region"` + AmpCloudRegionEstServer types.String `tfsdk:"amp_cloud_region_est_server"` + AlertLogLevel types.String `tfsdk:"alert_log_level"` + FileAnalysis types.Bool `tfsdk:"file_analysis"` + FileAnalysisCloudRegion types.String `tfsdk:"file_analysis_cloud_region"` + FileAnalysisFileTypes types.Set `tfsdk:"file_analysis_file_types"` + FileAnalysisAlertLogLevel types.String `tfsdk:"file_analysis_alert_log_level"` +} + +// End of section. //template:end types + +// Section below is generated&owned by "gen/generator.go". //template:begin getModel +func (data PolicyObjectUnifiedAdvancedMalwareProtection) getModel() string { + return "policy_object_unified_advanced_malware_protection" +} + +// End of section. //template:end getModel + +// Section below is generated&owned by "gen/generator.go". //template:begin getPath +func (data PolicyObjectUnifiedAdvancedMalwareProtection) getPath() string { + return fmt.Sprintf("/v1/feature-profile/sdwan/policy-object/%v/unified/advanced-malware-protection", url.QueryEscape(data.FeatureProfileId.ValueString())) +} + +// End of section. //template:end getPath + +// Section below is generated&owned by "gen/generator.go". //template:begin toBody +func (data PolicyObjectUnifiedAdvancedMalwareProtection) toBody(ctx context.Context) string { + body := "" + body, _ = sjson.Set(body, "name", data.Name.ValueString()) + body, _ = sjson.Set(body, "description", data.Description.ValueString()) + path := "data." + if !data.MatchAllVpn.IsNull() { + if true { + body, _ = sjson.Set(body, path+"matchAllVpn.optionType", "global") + body, _ = sjson.Set(body, path+"matchAllVpn.value", data.MatchAllVpn.ValueBool()) + } + } + if !data.AmpCloudRegion.IsNull() { + if true { + body, _ = sjson.Set(body, path+"fileReputationCloudServer.optionType", "global") + body, _ = sjson.Set(body, path+"fileReputationCloudServer.value", data.AmpCloudRegion.ValueString()) + } + } + if !data.AmpCloudRegionEstServer.IsNull() { + if true { + body, _ = sjson.Set(body, path+"fileReputationEstServer.optionType", "global") + body, _ = sjson.Set(body, path+"fileReputationEstServer.value", data.AmpCloudRegionEstServer.ValueString()) + } + } + if !data.AlertLogLevel.IsNull() { + if true { + body, _ = sjson.Set(body, path+"fileReputationAlert.optionType", "global") + body, _ = sjson.Set(body, path+"fileReputationAlert.value", data.AlertLogLevel.ValueString()) + } + } + if !data.FileAnalysis.IsNull() { + if true { + body, _ = sjson.Set(body, path+"fileAnalysisEnabled.optionType", "global") + body, _ = sjson.Set(body, path+"fileAnalysisEnabled.value", data.FileAnalysis.ValueBool()) + } + } + if !data.FileAnalysisCloudRegion.IsNull() { + if true { + body, _ = sjson.Set(body, path+"fileAnalysisCloudServer.optionType", "global") + body, _ = sjson.Set(body, path+"fileAnalysisCloudServer.value", data.FileAnalysisCloudRegion.ValueString()) + } + } + if !data.FileAnalysisFileTypes.IsNull() { + if true { + body, _ = sjson.Set(body, path+"fileAnalysisFileTypes.optionType", "global") + var values []string + data.FileAnalysisFileTypes.ElementsAs(ctx, &values, false) + body, _ = sjson.Set(body, path+"fileAnalysisFileTypes.value", values) + } + } + if !data.FileAnalysisAlertLogLevel.IsNull() { + if true { + body, _ = sjson.Set(body, path+"fileAnalysisAlert.optionType", "global") + body, _ = sjson.Set(body, path+"fileAnalysisAlert.value", data.FileAnalysisAlertLogLevel.ValueString()) + } + } + return body +} + +// End of section. //template:end toBody + +// Section below is generated&owned by "gen/generator.go". //template:begin fromBody +func (data *PolicyObjectUnifiedAdvancedMalwareProtection) fromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.MatchAllVpn = types.BoolNull() + + if t := res.Get(path + "matchAllVpn.optionType"); t.Exists() { + va := res.Get(path + "matchAllVpn.value") + if t.String() == "global" { + data.MatchAllVpn = types.BoolValue(va.Bool()) + } + } + data.AmpCloudRegion = types.StringNull() + + if t := res.Get(path + "fileReputationCloudServer.optionType"); t.Exists() { + va := res.Get(path + "fileReputationCloudServer.value") + if t.String() == "global" { + data.AmpCloudRegion = types.StringValue(va.String()) + } + } + data.AmpCloudRegionEstServer = types.StringNull() + + if t := res.Get(path + "fileReputationEstServer.optionType"); t.Exists() { + va := res.Get(path + "fileReputationEstServer.value") + if t.String() == "global" { + data.AmpCloudRegionEstServer = types.StringValue(va.String()) + } + } + data.AlertLogLevel = types.StringNull() + + if t := res.Get(path + "fileReputationAlert.optionType"); t.Exists() { + va := res.Get(path + "fileReputationAlert.value") + if t.String() == "global" { + data.AlertLogLevel = types.StringValue(va.String()) + } + } + data.FileAnalysis = types.BoolNull() + + if t := res.Get(path + "fileAnalysisEnabled.optionType"); t.Exists() { + va := res.Get(path + "fileAnalysisEnabled.value") + if t.String() == "global" { + data.FileAnalysis = types.BoolValue(va.Bool()) + } + } + data.FileAnalysisCloudRegion = types.StringNull() + + if t := res.Get(path + "fileAnalysisCloudServer.optionType"); t.Exists() { + va := res.Get(path + "fileAnalysisCloudServer.value") + if t.String() == "global" { + data.FileAnalysisCloudRegion = types.StringValue(va.String()) + } + } + data.FileAnalysisFileTypes = types.SetNull(types.StringType) + + if t := res.Get(path + "fileAnalysisFileTypes.optionType"); t.Exists() { + va := res.Get(path + "fileAnalysisFileTypes.value") + if t.String() == "global" { + data.FileAnalysisFileTypes = helpers.GetStringSet(va.Array()) + } + } + data.FileAnalysisAlertLogLevel = types.StringNull() + + if t := res.Get(path + "fileAnalysisAlert.optionType"); t.Exists() { + va := res.Get(path + "fileAnalysisAlert.value") + if t.String() == "global" { + data.FileAnalysisAlertLogLevel = types.StringValue(va.String()) + } + } +} + +// End of section. //template:end fromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin updateFromBody +func (data *PolicyObjectUnifiedAdvancedMalwareProtection) updateFromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.MatchAllVpn = types.BoolNull() + + if t := res.Get(path + "matchAllVpn.optionType"); t.Exists() { + va := res.Get(path + "matchAllVpn.value") + if t.String() == "global" { + data.MatchAllVpn = types.BoolValue(va.Bool()) + } + } + data.AmpCloudRegion = types.StringNull() + + if t := res.Get(path + "fileReputationCloudServer.optionType"); t.Exists() { + va := res.Get(path + "fileReputationCloudServer.value") + if t.String() == "global" { + data.AmpCloudRegion = types.StringValue(va.String()) + } + } + data.AmpCloudRegionEstServer = types.StringNull() + + if t := res.Get(path + "fileReputationEstServer.optionType"); t.Exists() { + va := res.Get(path + "fileReputationEstServer.value") + if t.String() == "global" { + data.AmpCloudRegionEstServer = types.StringValue(va.String()) + } + } + data.AlertLogLevel = types.StringNull() + + if t := res.Get(path + "fileReputationAlert.optionType"); t.Exists() { + va := res.Get(path + "fileReputationAlert.value") + if t.String() == "global" { + data.AlertLogLevel = types.StringValue(va.String()) + } + } + data.FileAnalysis = types.BoolNull() + + if t := res.Get(path + "fileAnalysisEnabled.optionType"); t.Exists() { + va := res.Get(path + "fileAnalysisEnabled.value") + if t.String() == "global" { + data.FileAnalysis = types.BoolValue(va.Bool()) + } + } + data.FileAnalysisCloudRegion = types.StringNull() + + if t := res.Get(path + "fileAnalysisCloudServer.optionType"); t.Exists() { + va := res.Get(path + "fileAnalysisCloudServer.value") + if t.String() == "global" { + data.FileAnalysisCloudRegion = types.StringValue(va.String()) + } + } + data.FileAnalysisFileTypes = types.SetNull(types.StringType) + + if t := res.Get(path + "fileAnalysisFileTypes.optionType"); t.Exists() { + va := res.Get(path + "fileAnalysisFileTypes.value") + if t.String() == "global" { + data.FileAnalysisFileTypes = helpers.GetStringSet(va.Array()) + } + } + data.FileAnalysisAlertLogLevel = types.StringNull() + + if t := res.Get(path + "fileAnalysisAlert.optionType"); t.Exists() { + va := res.Get(path + "fileAnalysisAlert.value") + if t.String() == "global" { + data.FileAnalysisAlertLogLevel = types.StringValue(va.String()) + } + } +} + +// End of section. //template:end updateFromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin isNull +func (data *PolicyObjectUnifiedAdvancedMalwareProtection) isNull(ctx context.Context, res gjson.Result) bool { + if !data.FeatureProfileId.IsNull() { + return false + } + if !data.MatchAllVpn.IsNull() { + return false + } + if !data.AmpCloudRegion.IsNull() { + return false + } + if !data.AmpCloudRegionEstServer.IsNull() { + return false + } + if !data.AlertLogLevel.IsNull() { + return false + } + if !data.FileAnalysis.IsNull() { + return false + } + if !data.FileAnalysisCloudRegion.IsNull() { + return false + } + if !data.FileAnalysisFileTypes.IsNull() { + return false + } + if !data.FileAnalysisAlertLogLevel.IsNull() { + return false + } + return true +} + +// End of section. //template:end isNull diff --git a/internal/provider/provider.go b/internal/provider/provider.go index 845eb832..49eba9bb 100644 --- a/internal/provider/provider.go +++ b/internal/provider/provider.go @@ -298,6 +298,7 @@ func (p *SdwanProvider) Resources(ctx context.Context) []func() resource.Resourc NewPolicyObjectPolicerProfileParcelResource, NewPolicyObjectSLAClassListProfileParcelResource, NewPolicyObjectTLOCListProfileParcelResource, + NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource, NewServiceLANVPNProfileParcelResource, NewServiceLANVPNInterfaceEthernetProfileParcelResource, NewServiceLANVPNInterfaceGREProfileParcelResource, @@ -480,6 +481,7 @@ func (p *SdwanProvider) DataSources(ctx context.Context) []func() datasource.Dat NewPolicyObjectPolicerProfileParcelDataSource, NewPolicyObjectSLAClassListProfileParcelDataSource, NewPolicyObjectTLOCListProfileParcelDataSource, + NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource, NewServiceLANVPNProfileParcelDataSource, NewServiceLANVPNInterfaceEthernetProfileParcelDataSource, NewServiceLANVPNInterfaceGREProfileParcelDataSource, diff --git a/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection.go b/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection.go new file mode 100644 index 00000000..e3aed7bf --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection.go @@ -0,0 +1,290 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + "sync" + + "github.com/CiscoDevNet/terraform-provider-sdwan/internal/provider/helpers" + "github.com/hashicorp/terraform-plugin-framework-validators/stringvalidator" + "github.com/hashicorp/terraform-plugin-framework/path" + "github.com/hashicorp/terraform-plugin-framework/resource" + "github.com/hashicorp/terraform-plugin-framework/resource/schema" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/planmodifier" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/stringplanmodifier" + "github.com/hashicorp/terraform-plugin-framework/schema/validator" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure provider defined types fully satisfy framework interfaces +var _ resource.Resource = &PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource{} +var _ resource.ResourceWithImportState = &PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource{} + +func NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource() resource.Resource { + return &PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource{} +} + +type PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource struct { + client *sdwan.Client + updateMutex *sync.Mutex +} + +func (r *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource) Metadata(ctx context.Context, req resource.MetadataRequest, resp *resource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_advanced_malware_protection" +} + +func (r *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource) Schema(ctx context.Context, req resource.SchemaRequest, resp *resource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: helpers.NewAttributeDescription("This resource can manage a Policy Object Unified Advanced Malware Protection Policy_object.").AddMinimumVersionDescription("20.12.0").String, + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Computed: true, + PlanModifiers: []planmodifier.String{ + stringplanmodifier.UseStateForUnknown(), + }, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Required: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Optional: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Feature Profile ID").String, + Required: true, + }, + "match_all_vpn": schema.BoolAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + }, + "amp_cloud_region": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("nam", "eur", "apjc").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("nam", "eur", "apjc"), + }, + }, + "amp_cloud_region_est_server": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("nam", "eur", "apjc").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("nam", "eur", "apjc"), + }, + }, + "alert_log_level": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("critical", "warning", "info").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("critical", "warning", "info"), + }, + }, + "file_analysis": schema.BoolAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + }, + "file_analysis_cloud_region": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("nam", "eur").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("nam", "eur"), + }, + }, + "file_analysis_file_types": schema.SetAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + ElementType: types.StringType, + Required: true, + }, + "file_analysis_alert_log_level": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("critical", "warning", "info").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("critical", "warning", "info"), + }, + }, + }, + } +} + +func (r *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource) Configure(_ context.Context, req resource.ConfigureRequest, _ *resource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + r.client = req.ProviderData.(*SdwanProviderData).Client + r.updateMutex = req.ProviderData.(*SdwanProviderData).UpdateMutex +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin create +func (r *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource) Create(ctx context.Context, req resource.CreateRequest, resp *resource.CreateResponse) { + var plan PolicyObjectUnifiedAdvancedMalwareProtection + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Create", plan.Name.ValueString())) + + // Create object + body := plan.toBody(ctx) + + res, err := r.client.Post(plan.getPath(), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (POST), got error: %s, %s", err, res.String())) + return + } + + plan.Id = types.StringValue(res.Get("parcelId").String()) + plan.Version = types.Int64Value(0) + + tflog.Debug(ctx, fmt.Sprintf("%s: Create finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end create + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (r *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource) Read(ctx context.Context, req resource.ReadRequest, resp *resource.ReadResponse) { + var state PolicyObjectUnifiedAdvancedMalwareProtection + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", state.Name.String())) + + res, err := r.client.Get(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if res.Get("error.message").String() == "Invalid feature Id" { + resp.State.RemoveResource(ctx) + return + } else if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object (GET), got error: %s, %s", err, res.String())) + return + } + + // If every attribute is set to null we are dealing with an import operation and therefore reading all attributes + if state.isNull(ctx, res) { + state.fromBody(ctx, res) + } else { + state.updateFromBody(ctx, res) + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", state.Name.ValueString())) + + diags = resp.State.Set(ctx, &state) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read + +// Section below is generated&owned by "gen/generator.go". //template:begin update +func (r *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource) Update(ctx context.Context, req resource.UpdateRequest, resp *resource.UpdateResponse) { + var plan, state PolicyObjectUnifiedAdvancedMalwareProtection + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + // Read state + diags = req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Update", plan.Name.ValueString())) + + body := plan.toBody(ctx) + res, err := r.client.Put(plan.getPath()+"/"+url.QueryEscape(plan.Id.ValueString()), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (PUT), got error: %s, %s", err, res.String())) + return + } + + plan.Version = types.Int64Value(state.Version.ValueInt64() + 1) + + tflog.Debug(ctx, fmt.Sprintf("%s: Update finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end update + +// Section below is generated&owned by "gen/generator.go". //template:begin delete +func (r *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource) Delete(ctx context.Context, req resource.DeleteRequest, resp *resource.DeleteResponse) { + var state PolicyObjectUnifiedAdvancedMalwareProtection + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Delete", state.Name.ValueString())) + + res, err := r.client.Delete(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if err != nil && res.Get("error.message").String() != "Invalid Template Id" { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to delete object (DELETE), got error: %s, %s", err, res.String())) + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Delete finished successfully", state.Name.ValueString())) + + resp.State.RemoveResource(ctx) +} + +// End of section. //template:end delete + +// Section below is generated&owned by "gen/generator.go". //template:begin import +func (r *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource) ImportState(ctx context.Context, req resource.ImportStateRequest, resp *resource.ImportStateResponse) { + resource.ImportStatePassthroughID(ctx, path.Root("id"), req, resp) +} + +// End of section. //template:end import diff --git a/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection_test.go b/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection_test.go new file mode 100644 index 00000000..eb555f23 --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection_test.go @@ -0,0 +1,91 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAcc +func TestAccSdwanPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_malware_protection.test", "match_all_vpn", "true")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_malware_protection.test", "amp_cloud_region", "nam")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_malware_protection.test", "amp_cloud_region_est_server", "nam")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_malware_protection.test", "alert_log_level", "critical")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_malware_protection.test", "file_analysis", "true")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_malware_protection.test", "file_analysis_cloud_region", "nam")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_malware_protection.test", "file_analysis_alert_log_level", "critical")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + + { + Config: testAccSdwanPolicyObjectUnifiedAdvancedMalwareProtectionPrerequisitesProfileParcelConfig + testAccSdwanPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelConfig_all(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAcc + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccSdwanPolicyObjectUnifiedAdvancedMalwareProtectionPrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} + +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigMinimum + +// End of section. //template:end testAccConfigMinimum + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigAll +func testAccSdwanPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelConfig_all() string { + config := `resource "sdwan_policy_object_unified_advanced_malware_protection" "test" {` + "\n" + config += ` name = "TF_TEST_ALL"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` match_all_vpn = true` + "\n" + config += ` amp_cloud_region = "nam"` + "\n" + config += ` amp_cloud_region_est_server = "nam"` + "\n" + config += ` alert_log_level = "critical"` + "\n" + config += ` file_analysis = true` + "\n" + config += ` file_analysis_cloud_region = "nam"` + "\n" + config += ` file_analysis_file_types = ["pdf"]` + "\n" + config += ` file_analysis_alert_log_level = "critical"` + "\n" + config += `}` + "\n" + return config +} + +// End of section. //template:end testAccConfigAll diff --git a/templates/guides/changelog.md.tmpl b/templates/guides/changelog.md.tmpl index aed0b467..771e8438 100644 --- a/templates/guides/changelog.md.tmpl +++ b/templates/guides/changelog.md.tmpl @@ -11,6 +11,7 @@ description: |- - Add `sdwan_policy_object_application_list` resource and data source - Add `sdwan_policy_object_sla_class_list` resource and data source +- Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source ## 0.4.1 From 5ad649618c26afbe7737ff6aca2e5a51d3ac314a Mon Sep 17 00:00:00 2001 From: Sean Conroy Date: Fri, 13 Sep 2024 16:04:42 +0100 Subject: [PATCH 03/11] Add policy object unified url filtering resource and data source --- CHANGELOG.md | 1 + .../policy_object_unified_url_filtering.md | 44 +++ docs/guides/changelog.md | 1 + .../policy_object_unified_url_filtering.md | 68 ++++ .../data-source.tf | 4 + .../import.sh | 1 + .../resource.tf | 15 + .../policy_object_unified_url_filtering.yaml | 70 ++++ ... policy_object_unified_url_filtering.json} | 0 ...wan_policy_object_unified_url_filtering.go | 164 ++++++++ ...olicy_object_unified_url_filtering_test.go | 115 ++++++ ...wan_policy_object_unified_url_filtering.go | 368 ++++++++++++++++++ internal/provider/provider.go | 2 + ...wan_policy_object_unified_url_filtering.go | 303 ++++++++++++++ ...olicy_object_unified_url_filtering_test.go | 113 ++++++ templates/guides/changelog.md.tmpl | 1 + 16 files changed, 1270 insertions(+) create mode 100644 docs/data-sources/policy_object_unified_url_filtering.md create mode 100644 docs/resources/policy_object_unified_url_filtering.md create mode 100644 examples/data-sources/sdwan_policy_object_unified_url_filtering/data-source.tf create mode 100644 examples/resources/sdwan_policy_object_unified_url_filtering/import.sh create mode 100644 examples/resources/sdwan_policy_object_unified_url_filtering/resource.tf create mode 100644 gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml rename gen/models/profile_parcels/{policy_object_unified_advanced_url_filtering.json => policy_object_unified_url_filtering.json} (100%) create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_url_filtering.go create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_url_filtering_test.go create mode 100644 internal/provider/model_sdwan_policy_object_unified_url_filtering.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_url_filtering.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_url_filtering_test.go diff --git a/CHANGELOG.md b/CHANGELOG.md index c31847d7..37bc154f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -26,6 +26,7 @@ - Add `sdwan_service_routing_eigrp_feature` resource and data source - Add `sdwan_service_wireless_lan_feature` resource and data source - Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source +- Add `sdwan_policy_object_unified_url_filtering` resource and data source ## 0.4.1 diff --git a/docs/data-sources/policy_object_unified_url_filtering.md b/docs/data-sources/policy_object_unified_url_filtering.md new file mode 100644 index 00000000..77e9a063 --- /dev/null +++ b/docs/data-sources/policy_object_unified_url_filtering.md @@ -0,0 +1,44 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_url_filtering Data Source - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This data source can read the Policy Object Unified URL Filtering Policy_object. +--- + +# sdwan_policy_object_unified_url_filtering (Data Source) + +This data source can read the Policy Object Unified URL Filtering Policy_object. + +## Example Usage + +```terraform +data "sdwan_policy_object_unified_url_filtering" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} +``` + + +## Schema + +### Required + +- `feature_profile_id` (String) Feature Profile ID +- `id` (String) The id of the Policy_object + +### Read-Only + +- `alerts` (Set of String) +- `block_page_action` (String) +- `block_page_contents` (String) +- `description` (String) The description of the Policy_object +- `enable_alerts` (Boolean) +- `name` (String) The name of the Policy_object +- `redirect_url` (String) +- `url_allow_list_id` (String) +- `url_block_list_id` (String) +- `version` (Number) The version of the Policy_object +- `web_categories` (Set of String) +- `web_categories_action` (String) +- `web_reputation` (String) diff --git a/docs/guides/changelog.md b/docs/guides/changelog.md index 426deb44..fb96e5ea 100644 --- a/docs/guides/changelog.md +++ b/docs/guides/changelog.md @@ -35,6 +35,7 @@ description: |- - Add `sdwan_service_routing_eigrp_feature` resource and data source - Add `sdwan_service_wireless_lan_feature` resource and data source - Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source +- Add `sdwan_policy_object_unified_url_filtering` resource and data source ## 0.4.1 diff --git a/docs/resources/policy_object_unified_url_filtering.md b/docs/resources/policy_object_unified_url_filtering.md new file mode 100644 index 00000000..40d5587e --- /dev/null +++ b/docs/resources/policy_object_unified_url_filtering.md @@ -0,0 +1,68 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_url_filtering Resource - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This resource can manage a Policy Object Unified URL Filtering Policy_object. + Minimum SD-WAN Manager version: 20.12.0 +--- + +# sdwan_policy_object_unified_url_filtering (Resource) + +This resource can manage a Policy Object Unified URL Filtering Policy_object. + - Minimum SD-WAN Manager version: `20.12.0` + +## Example Usage + +```terraform +resource "sdwan_policy_object_unified_url_filtering" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + web_categories_action = "block" + web_categories = ["confirmed-spam-sources"] + web_reputation = "suspicious" + url_allow_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + url_block_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + block_page_action = "text" + block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator" + redirect_url = "www.example.com" + enable_alerts = true + alerts = ["blacklist"] +} +``` + + +## Schema + +### Required + +- `alerts` (Set of String) +- `block_page_action` (String) - Choices: `text`, `redirect-url` +- `block_page_contents` (String) +- `enable_alerts` (Boolean) +- `feature_profile_id` (String) Feature Profile ID +- `name` (String) The name of the Policy_object +- `redirect_url` (String) +- `url_allow_list_id` (String) +- `url_block_list_id` (String) +- `web_categories` (Set of String) +- `web_categories_action` (String) - Choices: `block`, `allow` +- `web_reputation` (String) - Choices: `high-risk`, `low-risk`, `moderate-risk`, `suspicious`, `trustworthy` + +### Optional + +- `description` (String) The description of the Policy_object + +### Read-Only + +- `id` (String) The id of the Policy_object +- `version` (Number) The version of the Policy_object + +## Import + +Import is supported using the following syntax: + +```shell +terraform import sdwan_policy_object_unified_url_filtering.example "f6b2c44c-693c-4763-b010-895aa3d236bd" +``` diff --git a/examples/data-sources/sdwan_policy_object_unified_url_filtering/data-source.tf b/examples/data-sources/sdwan_policy_object_unified_url_filtering/data-source.tf new file mode 100644 index 00000000..3bdcaf6a --- /dev/null +++ b/examples/data-sources/sdwan_policy_object_unified_url_filtering/data-source.tf @@ -0,0 +1,4 @@ +data "sdwan_policy_object_unified_url_filtering" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} diff --git a/examples/resources/sdwan_policy_object_unified_url_filtering/import.sh b/examples/resources/sdwan_policy_object_unified_url_filtering/import.sh new file mode 100644 index 00000000..e3cfc74f --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_url_filtering/import.sh @@ -0,0 +1 @@ +terraform import sdwan_policy_object_unified_url_filtering.example "f6b2c44c-693c-4763-b010-895aa3d236bd" diff --git a/examples/resources/sdwan_policy_object_unified_url_filtering/resource.tf b/examples/resources/sdwan_policy_object_unified_url_filtering/resource.tf new file mode 100644 index 00000000..553a6a0e --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_url_filtering/resource.tf @@ -0,0 +1,15 @@ +resource "sdwan_policy_object_unified_url_filtering" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + web_categories_action = "block" + web_categories = ["confirmed-spam-sources"] + web_reputation = "suspicious" + url_allow_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + url_block_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + block_page_action = "text" + block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator" + redirect_url = "www.example.com" + enable_alerts = true + alerts = ["blacklist"] +} diff --git a/gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml b/gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml new file mode 100644 index 00000000..d7f813b5 --- /dev/null +++ b/gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml @@ -0,0 +1,70 @@ +--- +name: Policy Object Unified URL Filtering +rest_endpoint: /v1/feature-profile/sdwan/policy-object/%v/unified/url-filtering +minimum_version: 20.12.0 +test_tags: [SDWAN_2012] +skip_minimum_test: true +parcel_type: policy_object +attributes: + - tf_name: feature_profile_id + reference: true + type: String + mandatory: true + description: Feature Profile ID + example: f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac + test_value: sdwan_policy_object_feature_profile.test.id + - model_name: webCategoriesAction + example: block + - model_name: webCategories + example: confirmed-spam-sources + - model_name: webReputation + example: suspicious + - model_name: refId + tf_name: url_allow_list_id + data_path: [urlAllowedList] + example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 + test_value: sdwan_policy_object_security_url_allow_list.test.id + - model_name: refId + tf_name: url_block_list_id + data_path: [urlBlockedList] + example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 + test_value: sdwan_policy_object_security_url_block_list.test.id + - model_name: blockPageAction + example: text + - model_name: blockPageContents + example: Access to the requested page has been denied. Please contact your Network Administrator + - model_name: redirectUrl + # exclude_test: true + example: www.example.com + - model_name: enableAlerts + example: true + - model_name: alerts + example: blacklist + +test_prerequisites: | + resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" + } + + resource "sdwan_policy_object_security_url_block_list" "test" { + name = "TF_TEST_ALLOW" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] + } + + resource "sdwan_policy_object_security_url_allow_list" "test" { + name = "TF_TEST_BLOCK" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] + } \ No newline at end of file diff --git a/gen/models/profile_parcels/policy_object_unified_advanced_url_filtering.json b/gen/models/profile_parcels/policy_object_unified_url_filtering.json similarity index 100% rename from gen/models/profile_parcels/policy_object_unified_advanced_url_filtering.json rename to gen/models/profile_parcels/policy_object_unified_url_filtering.json diff --git a/internal/provider/data_source_sdwan_policy_object_unified_url_filtering.go b/internal/provider/data_source_sdwan_policy_object_unified_url_filtering.go new file mode 100644 index 00000000..409a3633 --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_url_filtering.go @@ -0,0 +1,164 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/hashicorp/terraform-plugin-framework/datasource" + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure the implementation satisfies the expected interfaces. +var ( + _ datasource.DataSource = &PolicyObjectUnifiedURLFilteringProfileParcelDataSource{} + _ datasource.DataSourceWithConfigure = &PolicyObjectUnifiedURLFilteringProfileParcelDataSource{} +) + +func NewPolicyObjectUnifiedURLFilteringProfileParcelDataSource() datasource.DataSource { + return &PolicyObjectUnifiedURLFilteringProfileParcelDataSource{} +} + +type PolicyObjectUnifiedURLFilteringProfileParcelDataSource struct { + client *sdwan.Client +} + +func (d *PolicyObjectUnifiedURLFilteringProfileParcelDataSource) Metadata(_ context.Context, req datasource.MetadataRequest, resp *datasource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_url_filtering" +} + +func (d *PolicyObjectUnifiedURLFilteringProfileParcelDataSource) Schema(ctx context.Context, req datasource.SchemaRequest, resp *datasource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: "This data source can read the Policy Object Unified URL Filtering Policy_object.", + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Required: true, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Computed: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Computed: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: "Feature Profile ID", + Required: true, + }, + "web_categories_action": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "web_categories": schema.SetAttribute{ + MarkdownDescription: "", + ElementType: types.StringType, + Computed: true, + }, + "web_reputation": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "url_allow_list_id": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "url_block_list_id": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "block_page_action": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "block_page_contents": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "redirect_url": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "enable_alerts": schema.BoolAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "alerts": schema.SetAttribute{ + MarkdownDescription: "", + ElementType: types.StringType, + Computed: true, + }, + }, + } +} + +func (d *PolicyObjectUnifiedURLFilteringProfileParcelDataSource) Configure(_ context.Context, req datasource.ConfigureRequest, _ *datasource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + d.client = req.ProviderData.(*SdwanProviderData).Client +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (d *PolicyObjectUnifiedURLFilteringProfileParcelDataSource) Read(ctx context.Context, req datasource.ReadRequest, resp *datasource.ReadResponse) { + var config PolicyObjectUnifiedURLFiltering + + // Read config + diags := req.Config.Get(ctx, &config) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", config.Id.String())) + + res, err := d.client.Get(config.getPath() + "/" + url.QueryEscape(config.Id.ValueString())) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object, got error: %s", err)) + return + } + + config.fromBody(ctx, res) + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", config.Name.ValueString())) + + diags = resp.State.Set(ctx, &config) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read diff --git a/internal/provider/data_source_sdwan_policy_object_unified_url_filtering_test.go b/internal/provider/data_source_sdwan_policy_object_unified_url_filtering_test.go new file mode 100644 index 00000000..4ea0ddae --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_url_filtering_test.go @@ -0,0 +1,115 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSource +func TestAccDataSourceSdwanPolicyObjectUnifiedURLFilteringProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_url_filtering.test", "web_categories_action", "block")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_url_filtering.test", "web_reputation", "suspicious")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_url_filtering.test", "block_page_action", "text")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_url_filtering.test", "block_page_contents", "Access to the requested page has been denied. Please contact your Network Administrator")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_url_filtering.test", "redirect_url", "www.example.com")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_url_filtering.test", "enable_alerts", "true")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + { + Config: testAccDataSourceSdwanPolicyObjectUnifiedURLFilteringPrerequisitesProfileParcelConfig + testAccDataSourceSdwanPolicyObjectUnifiedURLFilteringProfileParcelConfig(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAccDataSource + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccDataSourceSdwanPolicyObjectUnifiedURLFilteringPrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} + +resource "sdwan_policy_object_security_url_block_list" "test" { + name = "TF_TEST_ALLOW" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} + +resource "sdwan_policy_object_security_url_allow_list" "test" { + name = "TF_TEST_BLOCK" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSourceConfig +func testAccDataSourceSdwanPolicyObjectUnifiedURLFilteringProfileParcelConfig() string { + config := `resource "sdwan_policy_object_unified_url_filtering" "test" {` + "\n" + config += ` name = "TF_TEST"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` web_categories_action = "block"` + "\n" + config += ` web_categories = ["confirmed-spam-sources"]` + "\n" + config += ` web_reputation = "suspicious"` + "\n" + config += ` url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id` + "\n" + config += ` url_block_list_id = sdwan_policy_object_security_url_block_list.test.id` + "\n" + config += ` block_page_action = "text"` + "\n" + config += ` block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator"` + "\n" + config += ` redirect_url = "www.example.com"` + "\n" + config += ` enable_alerts = true` + "\n" + config += ` alerts = ["blacklist"]` + "\n" + config += `}` + "\n" + + config += ` + data "sdwan_policy_object_unified_url_filtering" "test" { + id = sdwan_policy_object_unified_url_filtering.test.id + feature_profile_id = sdwan_policy_object_feature_profile.test.id + } + ` + return config +} + +// End of section. //template:end testAccDataSourceConfig diff --git a/internal/provider/model_sdwan_policy_object_unified_url_filtering.go b/internal/provider/model_sdwan_policy_object_unified_url_filtering.go new file mode 100644 index 00000000..93c3cc31 --- /dev/null +++ b/internal/provider/model_sdwan_policy_object_unified_url_filtering.go @@ -0,0 +1,368 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/CiscoDevNet/terraform-provider-sdwan/internal/provider/helpers" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/tidwall/gjson" + "github.com/tidwall/sjson" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin types +type PolicyObjectUnifiedURLFiltering struct { + Id types.String `tfsdk:"id"` + Version types.Int64 `tfsdk:"version"` + Name types.String `tfsdk:"name"` + Description types.String `tfsdk:"description"` + FeatureProfileId types.String `tfsdk:"feature_profile_id"` + WebCategoriesAction types.String `tfsdk:"web_categories_action"` + WebCategories types.Set `tfsdk:"web_categories"` + WebReputation types.String `tfsdk:"web_reputation"` + UrlAllowListId types.String `tfsdk:"url_allow_list_id"` + UrlBlockListId types.String `tfsdk:"url_block_list_id"` + BlockPageAction types.String `tfsdk:"block_page_action"` + BlockPageContents types.String `tfsdk:"block_page_contents"` + RedirectUrl types.String `tfsdk:"redirect_url"` + EnableAlerts types.Bool `tfsdk:"enable_alerts"` + Alerts types.Set `tfsdk:"alerts"` +} + +// End of section. //template:end types + +// Section below is generated&owned by "gen/generator.go". //template:begin getModel +func (data PolicyObjectUnifiedURLFiltering) getModel() string { + return "policy_object_unified_url_filtering" +} + +// End of section. //template:end getModel + +// Section below is generated&owned by "gen/generator.go". //template:begin getPath +func (data PolicyObjectUnifiedURLFiltering) getPath() string { + return fmt.Sprintf("/v1/feature-profile/sdwan/policy-object/%v/unified/url-filtering", url.QueryEscape(data.FeatureProfileId.ValueString())) +} + +// End of section. //template:end getPath + +// Section below is generated&owned by "gen/generator.go". //template:begin toBody +func (data PolicyObjectUnifiedURLFiltering) toBody(ctx context.Context) string { + body := "" + body, _ = sjson.Set(body, "name", data.Name.ValueString()) + body, _ = sjson.Set(body, "description", data.Description.ValueString()) + path := "data." + if !data.WebCategoriesAction.IsNull() { + if true { + body, _ = sjson.Set(body, path+"webCategoriesAction.optionType", "global") + body, _ = sjson.Set(body, path+"webCategoriesAction.value", data.WebCategoriesAction.ValueString()) + } + } + if !data.WebCategories.IsNull() { + if true { + body, _ = sjson.Set(body, path+"webCategories.optionType", "global") + var values []string + data.WebCategories.ElementsAs(ctx, &values, false) + body, _ = sjson.Set(body, path+"webCategories.value", values) + } + } + if !data.WebReputation.IsNull() { + if true { + body, _ = sjson.Set(body, path+"webReputation.optionType", "global") + body, _ = sjson.Set(body, path+"webReputation.value", data.WebReputation.ValueString()) + } + } + if !data.UrlAllowListId.IsNull() { + if true { + body, _ = sjson.Set(body, path+"urlAllowedList.refId.optionType", "global") + body, _ = sjson.Set(body, path+"urlAllowedList.refId.value", data.UrlAllowListId.ValueString()) + } + } + if !data.UrlBlockListId.IsNull() { + if true { + body, _ = sjson.Set(body, path+"urlBlockedList.refId.optionType", "global") + body, _ = sjson.Set(body, path+"urlBlockedList.refId.value", data.UrlBlockListId.ValueString()) + } + } + if !data.BlockPageAction.IsNull() { + if true { + body, _ = sjson.Set(body, path+"blockPageAction.optionType", "global") + body, _ = sjson.Set(body, path+"blockPageAction.value", data.BlockPageAction.ValueString()) + } + } + if !data.BlockPageContents.IsNull() { + if true { + body, _ = sjson.Set(body, path+"blockPageContents.optionType", "global") + body, _ = sjson.Set(body, path+"blockPageContents.value", data.BlockPageContents.ValueString()) + } + } + if !data.RedirectUrl.IsNull() { + if true { + body, _ = sjson.Set(body, path+"redirectUrl.optionType", "global") + body, _ = sjson.Set(body, path+"redirectUrl.value", data.RedirectUrl.ValueString()) + } + } + if !data.EnableAlerts.IsNull() { + if true { + body, _ = sjson.Set(body, path+"enableAlerts.optionType", "global") + body, _ = sjson.Set(body, path+"enableAlerts.value", data.EnableAlerts.ValueBool()) + } + } + if !data.Alerts.IsNull() { + if true { + body, _ = sjson.Set(body, path+"alerts.optionType", "global") + var values []string + data.Alerts.ElementsAs(ctx, &values, false) + body, _ = sjson.Set(body, path+"alerts.value", values) + } + } + return body +} + +// End of section. //template:end toBody + +// Section below is generated&owned by "gen/generator.go". //template:begin fromBody +func (data *PolicyObjectUnifiedURLFiltering) fromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.WebCategoriesAction = types.StringNull() + + if t := res.Get(path + "webCategoriesAction.optionType"); t.Exists() { + va := res.Get(path + "webCategoriesAction.value") + if t.String() == "global" { + data.WebCategoriesAction = types.StringValue(va.String()) + } + } + data.WebCategories = types.SetNull(types.StringType) + + if t := res.Get(path + "webCategories.optionType"); t.Exists() { + va := res.Get(path + "webCategories.value") + if t.String() == "global" { + data.WebCategories = helpers.GetStringSet(va.Array()) + } + } + data.WebReputation = types.StringNull() + + if t := res.Get(path + "webReputation.optionType"); t.Exists() { + va := res.Get(path + "webReputation.value") + if t.String() == "global" { + data.WebReputation = types.StringValue(va.String()) + } + } + data.UrlAllowListId = types.StringNull() + + if t := res.Get(path + "urlAllowedList.refId.optionType"); t.Exists() { + va := res.Get(path + "urlAllowedList.refId.value") + if t.String() == "global" { + data.UrlAllowListId = types.StringValue(va.String()) + } + } + data.UrlBlockListId = types.StringNull() + + if t := res.Get(path + "urlBlockedList.refId.optionType"); t.Exists() { + va := res.Get(path + "urlBlockedList.refId.value") + if t.String() == "global" { + data.UrlBlockListId = types.StringValue(va.String()) + } + } + data.BlockPageAction = types.StringNull() + + if t := res.Get(path + "blockPageAction.optionType"); t.Exists() { + va := res.Get(path + "blockPageAction.value") + if t.String() == "global" { + data.BlockPageAction = types.StringValue(va.String()) + } + } + data.BlockPageContents = types.StringNull() + + if t := res.Get(path + "blockPageContents.optionType"); t.Exists() { + va := res.Get(path + "blockPageContents.value") + if t.String() == "global" { + data.BlockPageContents = types.StringValue(va.String()) + } + } + data.RedirectUrl = types.StringNull() + + if t := res.Get(path + "redirectUrl.optionType"); t.Exists() { + va := res.Get(path + "redirectUrl.value") + if t.String() == "global" { + data.RedirectUrl = types.StringValue(va.String()) + } + } + data.EnableAlerts = types.BoolNull() + + if t := res.Get(path + "enableAlerts.optionType"); t.Exists() { + va := res.Get(path + "enableAlerts.value") + if t.String() == "global" { + data.EnableAlerts = types.BoolValue(va.Bool()) + } + } + data.Alerts = types.SetNull(types.StringType) + + if t := res.Get(path + "alerts.optionType"); t.Exists() { + va := res.Get(path + "alerts.value") + if t.String() == "global" { + data.Alerts = helpers.GetStringSet(va.Array()) + } + } +} + +// End of section. //template:end fromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin updateFromBody +func (data *PolicyObjectUnifiedURLFiltering) updateFromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.WebCategoriesAction = types.StringNull() + + if t := res.Get(path + "webCategoriesAction.optionType"); t.Exists() { + va := res.Get(path + "webCategoriesAction.value") + if t.String() == "global" { + data.WebCategoriesAction = types.StringValue(va.String()) + } + } + data.WebCategories = types.SetNull(types.StringType) + + if t := res.Get(path + "webCategories.optionType"); t.Exists() { + va := res.Get(path + "webCategories.value") + if t.String() == "global" { + data.WebCategories = helpers.GetStringSet(va.Array()) + } + } + data.WebReputation = types.StringNull() + + if t := res.Get(path + "webReputation.optionType"); t.Exists() { + va := res.Get(path + "webReputation.value") + if t.String() == "global" { + data.WebReputation = types.StringValue(va.String()) + } + } + data.UrlAllowListId = types.StringNull() + + if t := res.Get(path + "urlAllowedList.refId.optionType"); t.Exists() { + va := res.Get(path + "urlAllowedList.refId.value") + if t.String() == "global" { + data.UrlAllowListId = types.StringValue(va.String()) + } + } + data.UrlBlockListId = types.StringNull() + + if t := res.Get(path + "urlBlockedList.refId.optionType"); t.Exists() { + va := res.Get(path + "urlBlockedList.refId.value") + if t.String() == "global" { + data.UrlBlockListId = types.StringValue(va.String()) + } + } + data.BlockPageAction = types.StringNull() + + if t := res.Get(path + "blockPageAction.optionType"); t.Exists() { + va := res.Get(path + "blockPageAction.value") + if t.String() == "global" { + data.BlockPageAction = types.StringValue(va.String()) + } + } + data.BlockPageContents = types.StringNull() + + if t := res.Get(path + "blockPageContents.optionType"); t.Exists() { + va := res.Get(path + "blockPageContents.value") + if t.String() == "global" { + data.BlockPageContents = types.StringValue(va.String()) + } + } + data.RedirectUrl = types.StringNull() + + if t := res.Get(path + "redirectUrl.optionType"); t.Exists() { + va := res.Get(path + "redirectUrl.value") + if t.String() == "global" { + data.RedirectUrl = types.StringValue(va.String()) + } + } + data.EnableAlerts = types.BoolNull() + + if t := res.Get(path + "enableAlerts.optionType"); t.Exists() { + va := res.Get(path + "enableAlerts.value") + if t.String() == "global" { + data.EnableAlerts = types.BoolValue(va.Bool()) + } + } + data.Alerts = types.SetNull(types.StringType) + + if t := res.Get(path + "alerts.optionType"); t.Exists() { + va := res.Get(path + "alerts.value") + if t.String() == "global" { + data.Alerts = helpers.GetStringSet(va.Array()) + } + } +} + +// End of section. //template:end updateFromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin isNull +func (data *PolicyObjectUnifiedURLFiltering) isNull(ctx context.Context, res gjson.Result) bool { + if !data.FeatureProfileId.IsNull() { + return false + } + if !data.WebCategoriesAction.IsNull() { + return false + } + if !data.WebCategories.IsNull() { + return false + } + if !data.WebReputation.IsNull() { + return false + } + if !data.UrlAllowListId.IsNull() { + return false + } + if !data.UrlBlockListId.IsNull() { + return false + } + if !data.BlockPageAction.IsNull() { + return false + } + if !data.BlockPageContents.IsNull() { + return false + } + if !data.RedirectUrl.IsNull() { + return false + } + if !data.EnableAlerts.IsNull() { + return false + } + if !data.Alerts.IsNull() { + return false + } + return true +} + +// End of section. //template:end isNull diff --git a/internal/provider/provider.go b/internal/provider/provider.go index bb2ab9f6..ca29f59e 100644 --- a/internal/provider/provider.go +++ b/internal/provider/provider.go @@ -314,6 +314,7 @@ func (p *SdwanProvider) Resources(ctx context.Context) []func() resource.Resourc NewPolicyObjectStandardCommunityListProfileParcelResource, NewPolicyObjectTLOCListProfileParcelResource, NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource, + NewPolicyObjectUnifiedURLFilteringProfileParcelResource, NewPolicyObjectVPNGroupProfileParcelResource, NewServiceLANVPNProfileParcelResource, NewServiceLANVPNInterfaceEthernetProfileParcelResource, @@ -519,6 +520,7 @@ func (p *SdwanProvider) DataSources(ctx context.Context) []func() datasource.Dat NewPolicyObjectStandardCommunityListProfileParcelDataSource, NewPolicyObjectTLOCListProfileParcelDataSource, NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource, + NewPolicyObjectUnifiedURLFilteringProfileParcelDataSource, NewPolicyObjectVPNGroupProfileParcelDataSource, NewServiceLANVPNProfileParcelDataSource, NewServiceLANVPNInterfaceEthernetProfileParcelDataSource, diff --git a/internal/provider/resource_sdwan_policy_object_unified_url_filtering.go b/internal/provider/resource_sdwan_policy_object_unified_url_filtering.go new file mode 100644 index 00000000..e52ec2ee --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_url_filtering.go @@ -0,0 +1,303 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + "regexp" + "sync" + + "github.com/CiscoDevNet/terraform-provider-sdwan/internal/provider/helpers" + "github.com/hashicorp/terraform-plugin-framework-validators/stringvalidator" + "github.com/hashicorp/terraform-plugin-framework/path" + "github.com/hashicorp/terraform-plugin-framework/resource" + "github.com/hashicorp/terraform-plugin-framework/resource/schema" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/planmodifier" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/stringplanmodifier" + "github.com/hashicorp/terraform-plugin-framework/schema/validator" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure provider defined types fully satisfy framework interfaces +var _ resource.Resource = &PolicyObjectUnifiedURLFilteringProfileParcelResource{} +var _ resource.ResourceWithImportState = &PolicyObjectUnifiedURLFilteringProfileParcelResource{} + +func NewPolicyObjectUnifiedURLFilteringProfileParcelResource() resource.Resource { + return &PolicyObjectUnifiedURLFilteringProfileParcelResource{} +} + +type PolicyObjectUnifiedURLFilteringProfileParcelResource struct { + client *sdwan.Client + updateMutex *sync.Mutex +} + +func (r *PolicyObjectUnifiedURLFilteringProfileParcelResource) Metadata(ctx context.Context, req resource.MetadataRequest, resp *resource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_url_filtering" +} + +func (r *PolicyObjectUnifiedURLFilteringProfileParcelResource) Schema(ctx context.Context, req resource.SchemaRequest, resp *resource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: helpers.NewAttributeDescription("This resource can manage a Policy Object Unified URL Filtering Policy_object.").AddMinimumVersionDescription("20.12.0").String, + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Computed: true, + PlanModifiers: []planmodifier.String{ + stringplanmodifier.UseStateForUnknown(), + }, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Required: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Optional: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Feature Profile ID").String, + Required: true, + }, + "web_categories_action": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("block", "allow").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("block", "allow"), + }, + }, + "web_categories": schema.SetAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + ElementType: types.StringType, + Required: true, + }, + "web_reputation": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy"), + }, + }, + "url_allow_list_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + Validators: []validator.String{ + stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), + }, + }, + "url_block_list_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + Validators: []validator.String{ + stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), + }, + }, + "block_page_action": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("text", "redirect-url").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("text", "redirect-url"), + }, + }, + "block_page_contents": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + }, + "redirect_url": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + Validators: []validator.String{ + stringvalidator.RegexMatches(regexp.MustCompile(`^(http://www\.|https://www\.|http://|https://)?[a-z0-9]+([\-\.]{1}[a-z0-9]+)*\.[a-z]{2,5}(:[0-9]{1,5})?(/.*)?$`), ""), + }, + }, + "enable_alerts": schema.BoolAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + }, + "alerts": schema.SetAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + ElementType: types.StringType, + Required: true, + }, + }, + } +} + +func (r *PolicyObjectUnifiedURLFilteringProfileParcelResource) Configure(_ context.Context, req resource.ConfigureRequest, _ *resource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + r.client = req.ProviderData.(*SdwanProviderData).Client + r.updateMutex = req.ProviderData.(*SdwanProviderData).UpdateMutex +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin create +func (r *PolicyObjectUnifiedURLFilteringProfileParcelResource) Create(ctx context.Context, req resource.CreateRequest, resp *resource.CreateResponse) { + var plan PolicyObjectUnifiedURLFiltering + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Create", plan.Name.ValueString())) + + // Create object + body := plan.toBody(ctx) + + res, err := r.client.Post(plan.getPath(), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (POST), got error: %s, %s", err, res.String())) + return + } + + plan.Id = types.StringValue(res.Get("parcelId").String()) + plan.Version = types.Int64Value(0) + + tflog.Debug(ctx, fmt.Sprintf("%s: Create finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end create + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (r *PolicyObjectUnifiedURLFilteringProfileParcelResource) Read(ctx context.Context, req resource.ReadRequest, resp *resource.ReadResponse) { + var state PolicyObjectUnifiedURLFiltering + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", state.Name.String())) + + res, err := r.client.Get(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if res.Get("error.message").String() == "Invalid feature Id" { + resp.State.RemoveResource(ctx) + return + } else if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object (GET), got error: %s, %s", err, res.String())) + return + } + + // If every attribute is set to null we are dealing with an import operation and therefore reading all attributes + if state.isNull(ctx, res) { + state.fromBody(ctx, res) + } else { + state.updateFromBody(ctx, res) + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", state.Name.ValueString())) + + diags = resp.State.Set(ctx, &state) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read + +// Section below is generated&owned by "gen/generator.go". //template:begin update +func (r *PolicyObjectUnifiedURLFilteringProfileParcelResource) Update(ctx context.Context, req resource.UpdateRequest, resp *resource.UpdateResponse) { + var plan, state PolicyObjectUnifiedURLFiltering + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + // Read state + diags = req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Update", plan.Name.ValueString())) + + body := plan.toBody(ctx) + res, err := r.client.Put(plan.getPath()+"/"+url.QueryEscape(plan.Id.ValueString()), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (PUT), got error: %s, %s", err, res.String())) + return + } + + plan.Version = types.Int64Value(state.Version.ValueInt64() + 1) + + tflog.Debug(ctx, fmt.Sprintf("%s: Update finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end update + +// Section below is generated&owned by "gen/generator.go". //template:begin delete +func (r *PolicyObjectUnifiedURLFilteringProfileParcelResource) Delete(ctx context.Context, req resource.DeleteRequest, resp *resource.DeleteResponse) { + var state PolicyObjectUnifiedURLFiltering + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Delete", state.Name.ValueString())) + + res, err := r.client.Delete(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if err != nil && res.Get("error.message").String() != "Invalid Template Id" { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to delete object (DELETE), got error: %s, %s", err, res.String())) + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Delete finished successfully", state.Name.ValueString())) + + resp.State.RemoveResource(ctx) +} + +// End of section. //template:end delete + +// Section below is generated&owned by "gen/generator.go". //template:begin import +func (r *PolicyObjectUnifiedURLFilteringProfileParcelResource) ImportState(ctx context.Context, req resource.ImportStateRequest, resp *resource.ImportStateResponse) { + resource.ImportStatePassthroughID(ctx, path.Root("id"), req, resp) +} + +// End of section. //template:end import diff --git a/internal/provider/resource_sdwan_policy_object_unified_url_filtering_test.go b/internal/provider/resource_sdwan_policy_object_unified_url_filtering_test.go new file mode 100644 index 00000000..faad1e6f --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_url_filtering_test.go @@ -0,0 +1,113 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAcc +func TestAccSdwanPolicyObjectUnifiedURLFilteringProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_url_filtering.test", "web_categories_action", "block")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_url_filtering.test", "web_reputation", "suspicious")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_url_filtering.test", "block_page_action", "text")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_url_filtering.test", "block_page_contents", "Access to the requested page has been denied. Please contact your Network Administrator")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_url_filtering.test", "redirect_url", "www.example.com")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_url_filtering.test", "enable_alerts", "true")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + + { + Config: testAccSdwanPolicyObjectUnifiedURLFilteringPrerequisitesProfileParcelConfig + testAccSdwanPolicyObjectUnifiedURLFilteringProfileParcelConfig_all(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAcc + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccSdwanPolicyObjectUnifiedURLFilteringPrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} + +resource "sdwan_policy_object_security_url_block_list" "test" { + name = "TF_TEST_ALLOW" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} + +resource "sdwan_policy_object_security_url_allow_list" "test" { + name = "TF_TEST_BLOCK" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigMinimum + +// End of section. //template:end testAccConfigMinimum + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigAll +func testAccSdwanPolicyObjectUnifiedURLFilteringProfileParcelConfig_all() string { + config := `resource "sdwan_policy_object_unified_url_filtering" "test" {` + "\n" + config += ` name = "TF_TEST_ALL"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` web_categories_action = "block"` + "\n" + config += ` web_categories = ["confirmed-spam-sources"]` + "\n" + config += ` web_reputation = "suspicious"` + "\n" + config += ` url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id` + "\n" + config += ` url_block_list_id = sdwan_policy_object_security_url_block_list.test.id` + "\n" + config += ` block_page_action = "text"` + "\n" + config += ` block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator"` + "\n" + config += ` redirect_url = "www.example.com"` + "\n" + config += ` enable_alerts = true` + "\n" + config += ` alerts = ["blacklist"]` + "\n" + config += `}` + "\n" + return config +} + +// End of section. //template:end testAccConfigAll diff --git a/templates/guides/changelog.md.tmpl b/templates/guides/changelog.md.tmpl index 426deb44..fb96e5ea 100644 --- a/templates/guides/changelog.md.tmpl +++ b/templates/guides/changelog.md.tmpl @@ -35,6 +35,7 @@ description: |- - Add `sdwan_service_routing_eigrp_feature` resource and data source - Add `sdwan_service_wireless_lan_feature` resource and data source - Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source +- Add `sdwan_policy_object_unified_url_filtering` resource and data source ## 0.4.1 From cf586b356e3dcb5d8173038078fdf05b8c45291d Mon Sep 17 00:00:00 2001 From: Sean Conroy Date: Fri, 13 Sep 2024 16:27:39 +0100 Subject: [PATCH 04/11] Add policy object unified tls ssl profile resource and data source --- CHANGELOG.md | 1 + .../policy_object_unified_tls_ssl_profile.md | 43 +++ docs/guides/changelog.md | 1 + .../policy_object_unified_tls_ssl_profile.md | 66 ++++ .../data-source.tf | 4 + .../import.sh | 1 + .../resource.tf | 14 + ...policy_object_unified_tls_ssl_profile.yaml | 71 ++++ ...olicy_object_unified_tls_ssl_profile.json} | 0 ...n_policy_object_unified_tls_ssl_profile.go | 161 ++++++++ ...icy_object_unified_tls_ssl_profile_test.go | 112 ++++++ ...n_policy_object_unified_tls_ssl_profile.go | 344 ++++++++++++++++++ internal/provider/provider.go | 2 + ...n_policy_object_unified_tls_ssl_profile.go | 294 +++++++++++++++ ...icy_object_unified_tls_ssl_profile_test.go | 110 ++++++ templates/guides/changelog.md.tmpl | 1 + 16 files changed, 1225 insertions(+) create mode 100644 docs/data-sources/policy_object_unified_tls_ssl_profile.md create mode 100644 docs/resources/policy_object_unified_tls_ssl_profile.md create mode 100644 examples/data-sources/sdwan_policy_object_unified_tls_ssl_profile/data-source.tf create mode 100644 examples/resources/sdwan_policy_object_unified_tls_ssl_profile/import.sh create mode 100644 examples/resources/sdwan_policy_object_unified_tls_ssl_profile/resource.tf create mode 100644 gen/definitions/profile_parcels/policy_object_unified_tls_ssl_profile.yaml rename gen/models/profile_parcels/{policy_object_unified_ssl_decryption_profile.json => policy_object_unified_tls_ssl_profile.json} (100%) create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_profile.go create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_profile_test.go create mode 100644 internal/provider/model_sdwan_policy_object_unified_tls_ssl_profile.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile_test.go diff --git a/CHANGELOG.md b/CHANGELOG.md index 37bc154f..d9cd7746 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -27,6 +27,7 @@ - Add `sdwan_service_wireless_lan_feature` resource and data source - Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source - Add `sdwan_policy_object_unified_url_filtering` resource and data source +- Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source ## 0.4.1 diff --git a/docs/data-sources/policy_object_unified_tls_ssl_profile.md b/docs/data-sources/policy_object_unified_tls_ssl_profile.md new file mode 100644 index 00000000..a7458b62 --- /dev/null +++ b/docs/data-sources/policy_object_unified_tls_ssl_profile.md @@ -0,0 +1,43 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_tls_ssl_profile Data Source - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This data source can read the Policy Object Unified TLS SSL Profile Policy_object. +--- + +# sdwan_policy_object_unified_tls_ssl_profile (Data Source) + +This data source can read the Policy Object Unified TLS SSL Profile Policy_object. + +## Example Usage + +```terraform +data "sdwan_policy_object_unified_tls_ssl_profile" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} +``` + + +## Schema + +### Required + +- `feature_profile_id` (String) Feature Profile ID +- `id` (String) The id of the Policy_object + +### Read-Only + +- `decrypt_categories` (Set of String) +- `decrypt_threshold` (String) +- `description` (String) The description of the Policy_object +- `fail_decrypt` (Boolean) +- `name` (String) The name of the Policy_object +- `no_decrypt_categories` (Set of String) +- `pass_through_categories` (Set of String) +- `reputation` (Boolean) +- `threshold_categories` (String) +- `url_allow_list_id` (String) +- `url_block_list_id` (String) +- `version` (Number) The version of the Policy_object diff --git a/docs/guides/changelog.md b/docs/guides/changelog.md index fb96e5ea..8fb73474 100644 --- a/docs/guides/changelog.md +++ b/docs/guides/changelog.md @@ -36,6 +36,7 @@ description: |- - Add `sdwan_service_wireless_lan_feature` resource and data source - Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source - Add `sdwan_policy_object_unified_url_filtering` resource and data source +- Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source ## 0.4.1 diff --git a/docs/resources/policy_object_unified_tls_ssl_profile.md b/docs/resources/policy_object_unified_tls_ssl_profile.md new file mode 100644 index 00000000..da157cfc --- /dev/null +++ b/docs/resources/policy_object_unified_tls_ssl_profile.md @@ -0,0 +1,66 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_tls_ssl_profile Resource - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This resource can manage a Policy Object Unified TLS SSL Profile Policy_object. + Minimum SD-WAN Manager version: 20.12.0 +--- + +# sdwan_policy_object_unified_tls_ssl_profile (Resource) + +This resource can manage a Policy Object Unified TLS SSL Profile Policy_object. + - Minimum SD-WAN Manager version: `20.12.0` + +## Example Usage + +```terraform +resource "sdwan_policy_object_unified_tls_ssl_profile" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + decrypt_categories = ["alcohol-and-tobacco"] + no_decrypt_categories = ["abortion"] + pass_through_categories = ["auctions"] + reputation = true + decrypt_threshold = "moderate-risk" + threshold_categories = "moderate-risk" + fail_decrypt = true + url_allow_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + url_block_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" +} +``` + + +## Schema + +### Required + +- `decrypt_categories` (Set of String) +- `decrypt_threshold` (String) - Choices: `high-risk`, `low-risk`, `moderate-risk`, `suspicious`, `trustworthy` +- `fail_decrypt` (Boolean) +- `feature_profile_id` (String) Feature Profile ID +- `name` (String) The name of the Policy_object +- `no_decrypt_categories` (Set of String) +- `pass_through_categories` (Set of String) +- `reputation` (Boolean) +- `threshold_categories` (String) - Choices: `high-risk`, `low-risk`, `moderate-risk`, `suspicious`, `trustworthy` +- `url_allow_list_id` (String) +- `url_block_list_id` (String) + +### Optional + +- `description` (String) The description of the Policy_object + +### Read-Only + +- `id` (String) The id of the Policy_object +- `version` (Number) The version of the Policy_object + +## Import + +Import is supported using the following syntax: + +```shell +terraform import sdwan_policy_object_unified_tls_ssl_profile.example "f6b2c44c-693c-4763-b010-895aa3d236bd" +``` diff --git a/examples/data-sources/sdwan_policy_object_unified_tls_ssl_profile/data-source.tf b/examples/data-sources/sdwan_policy_object_unified_tls_ssl_profile/data-source.tf new file mode 100644 index 00000000..b3381289 --- /dev/null +++ b/examples/data-sources/sdwan_policy_object_unified_tls_ssl_profile/data-source.tf @@ -0,0 +1,4 @@ +data "sdwan_policy_object_unified_tls_ssl_profile" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} diff --git a/examples/resources/sdwan_policy_object_unified_tls_ssl_profile/import.sh b/examples/resources/sdwan_policy_object_unified_tls_ssl_profile/import.sh new file mode 100644 index 00000000..9ddb84ac --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_tls_ssl_profile/import.sh @@ -0,0 +1 @@ +terraform import sdwan_policy_object_unified_tls_ssl_profile.example "f6b2c44c-693c-4763-b010-895aa3d236bd" diff --git a/examples/resources/sdwan_policy_object_unified_tls_ssl_profile/resource.tf b/examples/resources/sdwan_policy_object_unified_tls_ssl_profile/resource.tf new file mode 100644 index 00000000..12fbf013 --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_tls_ssl_profile/resource.tf @@ -0,0 +1,14 @@ +resource "sdwan_policy_object_unified_tls_ssl_profile" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + decrypt_categories = ["alcohol-and-tobacco"] + no_decrypt_categories = ["abortion"] + pass_through_categories = ["auctions"] + reputation = true + decrypt_threshold = "moderate-risk" + threshold_categories = "moderate-risk" + fail_decrypt = true + url_allow_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + url_block_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" +} diff --git a/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_profile.yaml b/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_profile.yaml new file mode 100644 index 00000000..33b43120 --- /dev/null +++ b/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_profile.yaml @@ -0,0 +1,71 @@ +--- +name: Policy Object Unified TLS SSL Profile +rest_endpoint: /v1/feature-profile/sdwan/policy-object/%v/unified/ssl-decryption-profile +minimum_version: 20.12.0 +test_tags: [SDWAN_2012] +skip_minimum_test: true +parcel_type: policy_object +attributes: + - tf_name: feature_profile_id + reference: true + type: String + mandatory: true + description: Feature Profile ID + example: f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac + test_value: sdwan_policy_object_feature_profile.test.id + - model_name: decryptCategories + example: alcohol-and-tobacco + - model_name: neverDecryptCategories + tf_name: no_decrypt_categories + example: abortion + - model_name: skipDecryptCategories + tf_name: pass_through_categories + example: auctions + - model_name: reputation + example: true + - model_name: decryptThreshold + example: moderate-risk + - model_name: skipDecryptThreshold + tf_name: threshold_categories + example: moderate-risk + - model_name: failDecrypt + example: true + - model_name: refId + tf_name: url_allow_list_id + data_path: [urlAllowedList] + example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 + test_value: sdwan_policy_object_security_url_allow_list.test.id + - model_name: refId + tf_name: url_block_list_id + data_path: [urlBlockedList] + example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 + test_value: sdwan_policy_object_security_url_block_list.test.id + + +test_prerequisites: | + resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" + } + + resource "sdwan_policy_object_security_url_block_list" "test" { + name = "TF_TEST_ALLOW" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] + } + + resource "sdwan_policy_object_security_url_allow_list" "test" { + name = "TF_TEST_BLOCK" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] + } \ No newline at end of file diff --git a/gen/models/profile_parcels/policy_object_unified_ssl_decryption_profile.json b/gen/models/profile_parcels/policy_object_unified_tls_ssl_profile.json similarity index 100% rename from gen/models/profile_parcels/policy_object_unified_ssl_decryption_profile.json rename to gen/models/profile_parcels/policy_object_unified_tls_ssl_profile.json diff --git a/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_profile.go b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_profile.go new file mode 100644 index 00000000..35aa2032 --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_profile.go @@ -0,0 +1,161 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/hashicorp/terraform-plugin-framework/datasource" + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure the implementation satisfies the expected interfaces. +var ( + _ datasource.DataSource = &PolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource{} + _ datasource.DataSourceWithConfigure = &PolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource{} +) + +func NewPolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource() datasource.DataSource { + return &PolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource{} +} + +type PolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource struct { + client *sdwan.Client +} + +func (d *PolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource) Metadata(_ context.Context, req datasource.MetadataRequest, resp *datasource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_tls_ssl_profile" +} + +func (d *PolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource) Schema(ctx context.Context, req datasource.SchemaRequest, resp *datasource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: "This data source can read the Policy Object Unified TLS SSL Profile Policy_object.", + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Required: true, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Computed: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Computed: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: "Feature Profile ID", + Required: true, + }, + "decrypt_categories": schema.SetAttribute{ + MarkdownDescription: "", + ElementType: types.StringType, + Computed: true, + }, + "no_decrypt_categories": schema.SetAttribute{ + MarkdownDescription: "", + ElementType: types.StringType, + Computed: true, + }, + "pass_through_categories": schema.SetAttribute{ + MarkdownDescription: "", + ElementType: types.StringType, + Computed: true, + }, + "reputation": schema.BoolAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "decrypt_threshold": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "threshold_categories": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "fail_decrypt": schema.BoolAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "url_allow_list_id": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "url_block_list_id": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + }, + } +} + +func (d *PolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource) Configure(_ context.Context, req datasource.ConfigureRequest, _ *datasource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + d.client = req.ProviderData.(*SdwanProviderData).Client +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (d *PolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource) Read(ctx context.Context, req datasource.ReadRequest, resp *datasource.ReadResponse) { + var config PolicyObjectUnifiedTLSSSLProfile + + // Read config + diags := req.Config.Get(ctx, &config) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", config.Id.String())) + + res, err := d.client.Get(config.getPath() + "/" + url.QueryEscape(config.Id.ValueString())) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object, got error: %s", err)) + return + } + + config.fromBody(ctx, res) + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", config.Name.ValueString())) + + diags = resp.State.Set(ctx, &config) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read diff --git a/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_profile_test.go b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_profile_test.go new file mode 100644 index 00000000..26d93525 --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_profile_test.go @@ -0,0 +1,112 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSource +func TestAccDataSourceSdwanPolicyObjectUnifiedTLSSSLProfileProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_profile.test", "reputation", "true")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_profile.test", "decrypt_threshold", "moderate-risk")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_profile.test", "threshold_categories", "moderate-risk")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_profile.test", "fail_decrypt", "true")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + { + Config: testAccDataSourceSdwanPolicyObjectUnifiedTLSSSLProfilePrerequisitesProfileParcelConfig + testAccDataSourceSdwanPolicyObjectUnifiedTLSSSLProfileProfileParcelConfig(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAccDataSource + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccDataSourceSdwanPolicyObjectUnifiedTLSSSLProfilePrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} + +resource "sdwan_policy_object_security_url_block_list" "test" { + name = "TF_TEST_ALLOW" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} + +resource "sdwan_policy_object_security_url_allow_list" "test" { + name = "TF_TEST_BLOCK" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSourceConfig +func testAccDataSourceSdwanPolicyObjectUnifiedTLSSSLProfileProfileParcelConfig() string { + config := `resource "sdwan_policy_object_unified_tls_ssl_profile" "test" {` + "\n" + config += ` name = "TF_TEST"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` decrypt_categories = ["alcohol-and-tobacco"]` + "\n" + config += ` no_decrypt_categories = ["abortion"]` + "\n" + config += ` pass_through_categories = ["auctions"]` + "\n" + config += ` reputation = true` + "\n" + config += ` decrypt_threshold = "moderate-risk"` + "\n" + config += ` threshold_categories = "moderate-risk"` + "\n" + config += ` fail_decrypt = true` + "\n" + config += ` url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id` + "\n" + config += ` url_block_list_id = sdwan_policy_object_security_url_block_list.test.id` + "\n" + config += `}` + "\n" + + config += ` + data "sdwan_policy_object_unified_tls_ssl_profile" "test" { + id = sdwan_policy_object_unified_tls_ssl_profile.test.id + feature_profile_id = sdwan_policy_object_feature_profile.test.id + } + ` + return config +} + +// End of section. //template:end testAccDataSourceConfig diff --git a/internal/provider/model_sdwan_policy_object_unified_tls_ssl_profile.go b/internal/provider/model_sdwan_policy_object_unified_tls_ssl_profile.go new file mode 100644 index 00000000..0aafb56a --- /dev/null +++ b/internal/provider/model_sdwan_policy_object_unified_tls_ssl_profile.go @@ -0,0 +1,344 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/CiscoDevNet/terraform-provider-sdwan/internal/provider/helpers" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/tidwall/gjson" + "github.com/tidwall/sjson" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin types +type PolicyObjectUnifiedTLSSSLProfile struct { + Id types.String `tfsdk:"id"` + Version types.Int64 `tfsdk:"version"` + Name types.String `tfsdk:"name"` + Description types.String `tfsdk:"description"` + FeatureProfileId types.String `tfsdk:"feature_profile_id"` + DecryptCategories types.Set `tfsdk:"decrypt_categories"` + NoDecryptCategories types.Set `tfsdk:"no_decrypt_categories"` + PassThroughCategories types.Set `tfsdk:"pass_through_categories"` + Reputation types.Bool `tfsdk:"reputation"` + DecryptThreshold types.String `tfsdk:"decrypt_threshold"` + ThresholdCategories types.String `tfsdk:"threshold_categories"` + FailDecrypt types.Bool `tfsdk:"fail_decrypt"` + UrlAllowListId types.String `tfsdk:"url_allow_list_id"` + UrlBlockListId types.String `tfsdk:"url_block_list_id"` +} + +// End of section. //template:end types + +// Section below is generated&owned by "gen/generator.go". //template:begin getModel +func (data PolicyObjectUnifiedTLSSSLProfile) getModel() string { + return "policy_object_unified_tls_ssl_profile" +} + +// End of section. //template:end getModel + +// Section below is generated&owned by "gen/generator.go". //template:begin getPath +func (data PolicyObjectUnifiedTLSSSLProfile) getPath() string { + return fmt.Sprintf("/v1/feature-profile/sdwan/policy-object/%v/unified/ssl-decryption-profile", url.QueryEscape(data.FeatureProfileId.ValueString())) +} + +// End of section. //template:end getPath + +// Section below is generated&owned by "gen/generator.go". //template:begin toBody +func (data PolicyObjectUnifiedTLSSSLProfile) toBody(ctx context.Context) string { + body := "" + body, _ = sjson.Set(body, "name", data.Name.ValueString()) + body, _ = sjson.Set(body, "description", data.Description.ValueString()) + path := "data." + if !data.DecryptCategories.IsNull() { + if true { + body, _ = sjson.Set(body, path+"decryptCategories.optionType", "global") + var values []string + data.DecryptCategories.ElementsAs(ctx, &values, false) + body, _ = sjson.Set(body, path+"decryptCategories.value", values) + } + } + if !data.NoDecryptCategories.IsNull() { + if true { + body, _ = sjson.Set(body, path+"neverDecryptCategories.optionType", "global") + var values []string + data.NoDecryptCategories.ElementsAs(ctx, &values, false) + body, _ = sjson.Set(body, path+"neverDecryptCategories.value", values) + } + } + if !data.PassThroughCategories.IsNull() { + if true { + body, _ = sjson.Set(body, path+"skipDecryptCategories.optionType", "global") + var values []string + data.PassThroughCategories.ElementsAs(ctx, &values, false) + body, _ = sjson.Set(body, path+"skipDecryptCategories.value", values) + } + } + if !data.Reputation.IsNull() { + if true { + body, _ = sjson.Set(body, path+"reputation.optionType", "global") + body, _ = sjson.Set(body, path+"reputation.value", data.Reputation.ValueBool()) + } + } + if !data.DecryptThreshold.IsNull() { + if true { + body, _ = sjson.Set(body, path+"decryptThreshold.optionType", "global") + body, _ = sjson.Set(body, path+"decryptThreshold.value", data.DecryptThreshold.ValueString()) + } + } + if !data.ThresholdCategories.IsNull() { + if true { + body, _ = sjson.Set(body, path+"skipDecryptThreshold.optionType", "global") + body, _ = sjson.Set(body, path+"skipDecryptThreshold.value", data.ThresholdCategories.ValueString()) + } + } + if !data.FailDecrypt.IsNull() { + if true { + body, _ = sjson.Set(body, path+"failDecrypt.optionType", "global") + body, _ = sjson.Set(body, path+"failDecrypt.value", data.FailDecrypt.ValueBool()) + } + } + if !data.UrlAllowListId.IsNull() { + if true { + body, _ = sjson.Set(body, path+"urlAllowedList.refId.optionType", "global") + body, _ = sjson.Set(body, path+"urlAllowedList.refId.value", data.UrlAllowListId.ValueString()) + } + } + if !data.UrlBlockListId.IsNull() { + if true { + body, _ = sjson.Set(body, path+"urlBlockedList.refId.optionType", "global") + body, _ = sjson.Set(body, path+"urlBlockedList.refId.value", data.UrlBlockListId.ValueString()) + } + } + return body +} + +// End of section. //template:end toBody + +// Section below is generated&owned by "gen/generator.go". //template:begin fromBody +func (data *PolicyObjectUnifiedTLSSSLProfile) fromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.DecryptCategories = types.SetNull(types.StringType) + + if t := res.Get(path + "decryptCategories.optionType"); t.Exists() { + va := res.Get(path + "decryptCategories.value") + if t.String() == "global" { + data.DecryptCategories = helpers.GetStringSet(va.Array()) + } + } + data.NoDecryptCategories = types.SetNull(types.StringType) + + if t := res.Get(path + "neverDecryptCategories.optionType"); t.Exists() { + va := res.Get(path + "neverDecryptCategories.value") + if t.String() == "global" { + data.NoDecryptCategories = helpers.GetStringSet(va.Array()) + } + } + data.PassThroughCategories = types.SetNull(types.StringType) + + if t := res.Get(path + "skipDecryptCategories.optionType"); t.Exists() { + va := res.Get(path + "skipDecryptCategories.value") + if t.String() == "global" { + data.PassThroughCategories = helpers.GetStringSet(va.Array()) + } + } + data.Reputation = types.BoolNull() + + if t := res.Get(path + "reputation.optionType"); t.Exists() { + va := res.Get(path + "reputation.value") + if t.String() == "global" { + data.Reputation = types.BoolValue(va.Bool()) + } + } + data.DecryptThreshold = types.StringNull() + + if t := res.Get(path + "decryptThreshold.optionType"); t.Exists() { + va := res.Get(path + "decryptThreshold.value") + if t.String() == "global" { + data.DecryptThreshold = types.StringValue(va.String()) + } + } + data.ThresholdCategories = types.StringNull() + + if t := res.Get(path + "skipDecryptThreshold.optionType"); t.Exists() { + va := res.Get(path + "skipDecryptThreshold.value") + if t.String() == "global" { + data.ThresholdCategories = types.StringValue(va.String()) + } + } + data.FailDecrypt = types.BoolNull() + + if t := res.Get(path + "failDecrypt.optionType"); t.Exists() { + va := res.Get(path + "failDecrypt.value") + if t.String() == "global" { + data.FailDecrypt = types.BoolValue(va.Bool()) + } + } + data.UrlAllowListId = types.StringNull() + + if t := res.Get(path + "urlAllowedList.refId.optionType"); t.Exists() { + va := res.Get(path + "urlAllowedList.refId.value") + if t.String() == "global" { + data.UrlAllowListId = types.StringValue(va.String()) + } + } + data.UrlBlockListId = types.StringNull() + + if t := res.Get(path + "urlBlockedList.refId.optionType"); t.Exists() { + va := res.Get(path + "urlBlockedList.refId.value") + if t.String() == "global" { + data.UrlBlockListId = types.StringValue(va.String()) + } + } +} + +// End of section. //template:end fromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin updateFromBody +func (data *PolicyObjectUnifiedTLSSSLProfile) updateFromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.DecryptCategories = types.SetNull(types.StringType) + + if t := res.Get(path + "decryptCategories.optionType"); t.Exists() { + va := res.Get(path + "decryptCategories.value") + if t.String() == "global" { + data.DecryptCategories = helpers.GetStringSet(va.Array()) + } + } + data.NoDecryptCategories = types.SetNull(types.StringType) + + if t := res.Get(path + "neverDecryptCategories.optionType"); t.Exists() { + va := res.Get(path + "neverDecryptCategories.value") + if t.String() == "global" { + data.NoDecryptCategories = helpers.GetStringSet(va.Array()) + } + } + data.PassThroughCategories = types.SetNull(types.StringType) + + if t := res.Get(path + "skipDecryptCategories.optionType"); t.Exists() { + va := res.Get(path + "skipDecryptCategories.value") + if t.String() == "global" { + data.PassThroughCategories = helpers.GetStringSet(va.Array()) + } + } + data.Reputation = types.BoolNull() + + if t := res.Get(path + "reputation.optionType"); t.Exists() { + va := res.Get(path + "reputation.value") + if t.String() == "global" { + data.Reputation = types.BoolValue(va.Bool()) + } + } + data.DecryptThreshold = types.StringNull() + + if t := res.Get(path + "decryptThreshold.optionType"); t.Exists() { + va := res.Get(path + "decryptThreshold.value") + if t.String() == "global" { + data.DecryptThreshold = types.StringValue(va.String()) + } + } + data.ThresholdCategories = types.StringNull() + + if t := res.Get(path + "skipDecryptThreshold.optionType"); t.Exists() { + va := res.Get(path + "skipDecryptThreshold.value") + if t.String() == "global" { + data.ThresholdCategories = types.StringValue(va.String()) + } + } + data.FailDecrypt = types.BoolNull() + + if t := res.Get(path + "failDecrypt.optionType"); t.Exists() { + va := res.Get(path + "failDecrypt.value") + if t.String() == "global" { + data.FailDecrypt = types.BoolValue(va.Bool()) + } + } + data.UrlAllowListId = types.StringNull() + + if t := res.Get(path + "urlAllowedList.refId.optionType"); t.Exists() { + va := res.Get(path + "urlAllowedList.refId.value") + if t.String() == "global" { + data.UrlAllowListId = types.StringValue(va.String()) + } + } + data.UrlBlockListId = types.StringNull() + + if t := res.Get(path + "urlBlockedList.refId.optionType"); t.Exists() { + va := res.Get(path + "urlBlockedList.refId.value") + if t.String() == "global" { + data.UrlBlockListId = types.StringValue(va.String()) + } + } +} + +// End of section. //template:end updateFromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin isNull +func (data *PolicyObjectUnifiedTLSSSLProfile) isNull(ctx context.Context, res gjson.Result) bool { + if !data.FeatureProfileId.IsNull() { + return false + } + if !data.DecryptCategories.IsNull() { + return false + } + if !data.NoDecryptCategories.IsNull() { + return false + } + if !data.PassThroughCategories.IsNull() { + return false + } + if !data.Reputation.IsNull() { + return false + } + if !data.DecryptThreshold.IsNull() { + return false + } + if !data.ThresholdCategories.IsNull() { + return false + } + if !data.FailDecrypt.IsNull() { + return false + } + if !data.UrlAllowListId.IsNull() { + return false + } + if !data.UrlBlockListId.IsNull() { + return false + } + return true +} + +// End of section. //template:end isNull diff --git a/internal/provider/provider.go b/internal/provider/provider.go index ca29f59e..bb570926 100644 --- a/internal/provider/provider.go +++ b/internal/provider/provider.go @@ -314,6 +314,7 @@ func (p *SdwanProvider) Resources(ctx context.Context) []func() resource.Resourc NewPolicyObjectStandardCommunityListProfileParcelResource, NewPolicyObjectTLOCListProfileParcelResource, NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource, + NewPolicyObjectUnifiedTLSSSLProfileProfileParcelResource, NewPolicyObjectUnifiedURLFilteringProfileParcelResource, NewPolicyObjectVPNGroupProfileParcelResource, NewServiceLANVPNProfileParcelResource, @@ -520,6 +521,7 @@ func (p *SdwanProvider) DataSources(ctx context.Context) []func() datasource.Dat NewPolicyObjectStandardCommunityListProfileParcelDataSource, NewPolicyObjectTLOCListProfileParcelDataSource, NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource, + NewPolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource, NewPolicyObjectUnifiedURLFilteringProfileParcelDataSource, NewPolicyObjectVPNGroupProfileParcelDataSource, NewServiceLANVPNProfileParcelDataSource, diff --git a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile.go b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile.go new file mode 100644 index 00000000..c85d05ed --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile.go @@ -0,0 +1,294 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + "regexp" + "sync" + + "github.com/CiscoDevNet/terraform-provider-sdwan/internal/provider/helpers" + "github.com/hashicorp/terraform-plugin-framework-validators/stringvalidator" + "github.com/hashicorp/terraform-plugin-framework/path" + "github.com/hashicorp/terraform-plugin-framework/resource" + "github.com/hashicorp/terraform-plugin-framework/resource/schema" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/planmodifier" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/stringplanmodifier" + "github.com/hashicorp/terraform-plugin-framework/schema/validator" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure provider defined types fully satisfy framework interfaces +var _ resource.Resource = &PolicyObjectUnifiedTLSSSLProfileProfileParcelResource{} +var _ resource.ResourceWithImportState = &PolicyObjectUnifiedTLSSSLProfileProfileParcelResource{} + +func NewPolicyObjectUnifiedTLSSSLProfileProfileParcelResource() resource.Resource { + return &PolicyObjectUnifiedTLSSSLProfileProfileParcelResource{} +} + +type PolicyObjectUnifiedTLSSSLProfileProfileParcelResource struct { + client *sdwan.Client + updateMutex *sync.Mutex +} + +func (r *PolicyObjectUnifiedTLSSSLProfileProfileParcelResource) Metadata(ctx context.Context, req resource.MetadataRequest, resp *resource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_tls_ssl_profile" +} + +func (r *PolicyObjectUnifiedTLSSSLProfileProfileParcelResource) Schema(ctx context.Context, req resource.SchemaRequest, resp *resource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: helpers.NewAttributeDescription("This resource can manage a Policy Object Unified TLS SSL Profile Policy_object.").AddMinimumVersionDescription("20.12.0").String, + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Computed: true, + PlanModifiers: []planmodifier.String{ + stringplanmodifier.UseStateForUnknown(), + }, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Required: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Optional: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Feature Profile ID").String, + Required: true, + }, + "decrypt_categories": schema.SetAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + ElementType: types.StringType, + Required: true, + }, + "no_decrypt_categories": schema.SetAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + ElementType: types.StringType, + Required: true, + }, + "pass_through_categories": schema.SetAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + ElementType: types.StringType, + Required: true, + }, + "reputation": schema.BoolAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + }, + "decrypt_threshold": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy"), + }, + }, + "threshold_categories": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy"), + }, + }, + "fail_decrypt": schema.BoolAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + }, + "url_allow_list_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + Validators: []validator.String{ + stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), + }, + }, + "url_block_list_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + Validators: []validator.String{ + stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), + }, + }, + }, + } +} + +func (r *PolicyObjectUnifiedTLSSSLProfileProfileParcelResource) Configure(_ context.Context, req resource.ConfigureRequest, _ *resource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + r.client = req.ProviderData.(*SdwanProviderData).Client + r.updateMutex = req.ProviderData.(*SdwanProviderData).UpdateMutex +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin create +func (r *PolicyObjectUnifiedTLSSSLProfileProfileParcelResource) Create(ctx context.Context, req resource.CreateRequest, resp *resource.CreateResponse) { + var plan PolicyObjectUnifiedTLSSSLProfile + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Create", plan.Name.ValueString())) + + // Create object + body := plan.toBody(ctx) + + res, err := r.client.Post(plan.getPath(), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (POST), got error: %s, %s", err, res.String())) + return + } + + plan.Id = types.StringValue(res.Get("parcelId").String()) + plan.Version = types.Int64Value(0) + + tflog.Debug(ctx, fmt.Sprintf("%s: Create finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end create + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (r *PolicyObjectUnifiedTLSSSLProfileProfileParcelResource) Read(ctx context.Context, req resource.ReadRequest, resp *resource.ReadResponse) { + var state PolicyObjectUnifiedTLSSSLProfile + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", state.Name.String())) + + res, err := r.client.Get(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if res.Get("error.message").String() == "Invalid feature Id" { + resp.State.RemoveResource(ctx) + return + } else if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object (GET), got error: %s, %s", err, res.String())) + return + } + + // If every attribute is set to null we are dealing with an import operation and therefore reading all attributes + if state.isNull(ctx, res) { + state.fromBody(ctx, res) + } else { + state.updateFromBody(ctx, res) + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", state.Name.ValueString())) + + diags = resp.State.Set(ctx, &state) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read + +// Section below is generated&owned by "gen/generator.go". //template:begin update +func (r *PolicyObjectUnifiedTLSSSLProfileProfileParcelResource) Update(ctx context.Context, req resource.UpdateRequest, resp *resource.UpdateResponse) { + var plan, state PolicyObjectUnifiedTLSSSLProfile + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + // Read state + diags = req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Update", plan.Name.ValueString())) + + body := plan.toBody(ctx) + res, err := r.client.Put(plan.getPath()+"/"+url.QueryEscape(plan.Id.ValueString()), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (PUT), got error: %s, %s", err, res.String())) + return + } + + plan.Version = types.Int64Value(state.Version.ValueInt64() + 1) + + tflog.Debug(ctx, fmt.Sprintf("%s: Update finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end update + +// Section below is generated&owned by "gen/generator.go". //template:begin delete +func (r *PolicyObjectUnifiedTLSSSLProfileProfileParcelResource) Delete(ctx context.Context, req resource.DeleteRequest, resp *resource.DeleteResponse) { + var state PolicyObjectUnifiedTLSSSLProfile + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Delete", state.Name.ValueString())) + + res, err := r.client.Delete(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if err != nil && res.Get("error.message").String() != "Invalid Template Id" { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to delete object (DELETE), got error: %s, %s", err, res.String())) + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Delete finished successfully", state.Name.ValueString())) + + resp.State.RemoveResource(ctx) +} + +// End of section. //template:end delete + +// Section below is generated&owned by "gen/generator.go". //template:begin import +func (r *PolicyObjectUnifiedTLSSSLProfileProfileParcelResource) ImportState(ctx context.Context, req resource.ImportStateRequest, resp *resource.ImportStateResponse) { + resource.ImportStatePassthroughID(ctx, path.Root("id"), req, resp) +} + +// End of section. //template:end import diff --git a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile_test.go b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile_test.go new file mode 100644 index 00000000..9b69c74d --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile_test.go @@ -0,0 +1,110 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAcc +func TestAccSdwanPolicyObjectUnifiedTLSSSLProfileProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_profile.test", "reputation", "true")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_profile.test", "decrypt_threshold", "moderate-risk")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_profile.test", "threshold_categories", "moderate-risk")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_profile.test", "fail_decrypt", "true")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + + { + Config: testAccSdwanPolicyObjectUnifiedTLSSSLProfilePrerequisitesProfileParcelConfig + testAccSdwanPolicyObjectUnifiedTLSSSLProfileProfileParcelConfig_all(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAcc + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccSdwanPolicyObjectUnifiedTLSSSLProfilePrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} + +resource "sdwan_policy_object_security_url_block_list" "test" { + name = "TF_TEST_ALLOW" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} + +resource "sdwan_policy_object_security_url_allow_list" "test" { + name = "TF_TEST_BLOCK" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigMinimum + +// End of section. //template:end testAccConfigMinimum + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigAll +func testAccSdwanPolicyObjectUnifiedTLSSSLProfileProfileParcelConfig_all() string { + config := `resource "sdwan_policy_object_unified_tls_ssl_profile" "test" {` + "\n" + config += ` name = "TF_TEST_ALL"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` decrypt_categories = ["alcohol-and-tobacco"]` + "\n" + config += ` no_decrypt_categories = ["abortion"]` + "\n" + config += ` pass_through_categories = ["auctions"]` + "\n" + config += ` reputation = true` + "\n" + config += ` decrypt_threshold = "moderate-risk"` + "\n" + config += ` threshold_categories = "moderate-risk"` + "\n" + config += ` fail_decrypt = true` + "\n" + config += ` url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id` + "\n" + config += ` url_block_list_id = sdwan_policy_object_security_url_block_list.test.id` + "\n" + config += `}` + "\n" + return config +} + +// End of section. //template:end testAccConfigAll diff --git a/templates/guides/changelog.md.tmpl b/templates/guides/changelog.md.tmpl index fb96e5ea..8fb73474 100644 --- a/templates/guides/changelog.md.tmpl +++ b/templates/guides/changelog.md.tmpl @@ -36,6 +36,7 @@ description: |- - Add `sdwan_service_wireless_lan_feature` resource and data source - Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source - Add `sdwan_policy_object_unified_url_filtering` resource and data source +- Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source ## 0.4.1 From 24d0aa85f4012651690fd169ce52e6622a046a6b Mon Sep 17 00:00:00 2001 From: Sean Conroy Date: Fri, 13 Sep 2024 16:42:40 +0100 Subject: [PATCH 05/11] Add policy object unified intrusion prevention resource and data source --- CHANGELOG.md | 1 + ...icy_object_unified_intrusion_prevention.md | 39 +++ docs/guides/changelog.md | 1 + ...icy_object_unified_intrusion_prevention.md | 61 ++++ .../data-source.tf | 4 + .../import.sh | 1 + .../resource.tf | 10 + ...y_object_unified_intrusion_prevention.yaml | 46 +++ .../policy_object_unified_url_filtering.yaml | 1 - ...icy_object_unified_intrusion_prevention.go | 141 +++++++++ ...bject_unified_intrusion_prevention_test.go | 99 +++++++ ...icy_object_unified_intrusion_prevention.go | 233 +++++++++++++++ internal/provider/provider.go | 2 + ...icy_object_unified_intrusion_prevention.go | 275 ++++++++++++++++++ ...bject_unified_intrusion_prevention_test.go | 97 ++++++ templates/guides/changelog.md.tmpl | 1 + 16 files changed, 1011 insertions(+), 1 deletion(-) create mode 100644 docs/data-sources/policy_object_unified_intrusion_prevention.md create mode 100644 docs/resources/policy_object_unified_intrusion_prevention.md create mode 100644 examples/data-sources/sdwan_policy_object_unified_intrusion_prevention/data-source.tf create mode 100644 examples/resources/sdwan_policy_object_unified_intrusion_prevention/import.sh create mode 100644 examples/resources/sdwan_policy_object_unified_intrusion_prevention/resource.tf create mode 100644 gen/definitions/profile_parcels/policy_object_unified_intrusion_prevention.yaml create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention.go create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention_test.go create mode 100644 internal/provider/model_sdwan_policy_object_unified_intrusion_prevention.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention_test.go diff --git a/CHANGELOG.md b/CHANGELOG.md index d9cd7746..7b4f7c6e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -28,6 +28,7 @@ - Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source - Add `sdwan_policy_object_unified_url_filtering` resource and data source - Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source +- Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source ## 0.4.1 diff --git a/docs/data-sources/policy_object_unified_intrusion_prevention.md b/docs/data-sources/policy_object_unified_intrusion_prevention.md new file mode 100644 index 00000000..b2694adf --- /dev/null +++ b/docs/data-sources/policy_object_unified_intrusion_prevention.md @@ -0,0 +1,39 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_intrusion_prevention Data Source - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This data source can read the Policy Object Unified Intrusion Prevention Policy_object. +--- + +# sdwan_policy_object_unified_intrusion_prevention (Data Source) + +This data source can read the Policy Object Unified Intrusion Prevention Policy_object. + +## Example Usage + +```terraform +data "sdwan_policy_object_unified_intrusion_prevention" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} +``` + + +## Schema + +### Required + +- `feature_profile_id` (String) Feature Profile ID +- `id` (String) The id of the Policy_object + +### Read-Only + +- `custom_signature` (Boolean) Can be one of the enum value +- `description` (String) The description of the Policy_object +- `inspection_mode` (String) Can be one of the enum value +- `ips_signature_list_id` (String) +- `log_level` (String) Can be one of the enum value +- `name` (String) The name of the Policy_object +- `signature_set` (String) Can be one of the enum value +- `version` (Number) The version of the Policy_object diff --git a/docs/guides/changelog.md b/docs/guides/changelog.md index 8fb73474..27544a70 100644 --- a/docs/guides/changelog.md +++ b/docs/guides/changelog.md @@ -37,6 +37,7 @@ description: |- - Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source - Add `sdwan_policy_object_unified_url_filtering` resource and data source - Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source +- Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source ## 0.4.1 diff --git a/docs/resources/policy_object_unified_intrusion_prevention.md b/docs/resources/policy_object_unified_intrusion_prevention.md new file mode 100644 index 00000000..3ce12093 --- /dev/null +++ b/docs/resources/policy_object_unified_intrusion_prevention.md @@ -0,0 +1,61 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_intrusion_prevention Resource - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This resource can manage a Policy Object Unified Intrusion Prevention Policy_object. + Minimum SD-WAN Manager version: 20.12.0 +--- + +# sdwan_policy_object_unified_intrusion_prevention (Resource) + +This resource can manage a Policy Object Unified Intrusion Prevention Policy_object. + - Minimum SD-WAN Manager version: `20.12.0` + +## Example Usage + +```terraform +resource "sdwan_policy_object_unified_intrusion_prevention" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + signature_set = "balanced" + inspection_mode = "detection" + ips_signature_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + log_level = "error" + custom_signature = false +} +``` + + +## Schema + +### Required + +- `custom_signature` (Boolean) Can be one of the enum value +- `feature_profile_id` (String) Feature Profile ID +- `inspection_mode` (String) Can be one of the enum value + - Choices: `detection`, `protection` +- `ips_signature_list_id` (String) +- `log_level` (String) Can be one of the enum value + - Choices: `emergency`, `alert`, `critical`, `error`, `warning`, `notice`, `info`, `debug` +- `name` (String) The name of the Policy_object +- `signature_set` (String) Can be one of the enum value + - Choices: `balanced`, `connectivity`, `security` + +### Optional + +- `description` (String) The description of the Policy_object + +### Read-Only + +- `id` (String) The id of the Policy_object +- `version` (Number) The version of the Policy_object + +## Import + +Import is supported using the following syntax: + +```shell +terraform import sdwan_policy_object_unified_intrusion_prevention.example "f6b2c44c-693c-4763-b010-895aa3d236bd" +``` diff --git a/examples/data-sources/sdwan_policy_object_unified_intrusion_prevention/data-source.tf b/examples/data-sources/sdwan_policy_object_unified_intrusion_prevention/data-source.tf new file mode 100644 index 00000000..5fa19229 --- /dev/null +++ b/examples/data-sources/sdwan_policy_object_unified_intrusion_prevention/data-source.tf @@ -0,0 +1,4 @@ +data "sdwan_policy_object_unified_intrusion_prevention" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} diff --git a/examples/resources/sdwan_policy_object_unified_intrusion_prevention/import.sh b/examples/resources/sdwan_policy_object_unified_intrusion_prevention/import.sh new file mode 100644 index 00000000..2565c4fa --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_intrusion_prevention/import.sh @@ -0,0 +1 @@ +terraform import sdwan_policy_object_unified_intrusion_prevention.example "f6b2c44c-693c-4763-b010-895aa3d236bd" diff --git a/examples/resources/sdwan_policy_object_unified_intrusion_prevention/resource.tf b/examples/resources/sdwan_policy_object_unified_intrusion_prevention/resource.tf new file mode 100644 index 00000000..4c344961 --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_intrusion_prevention/resource.tf @@ -0,0 +1,10 @@ +resource "sdwan_policy_object_unified_intrusion_prevention" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + signature_set = "balanced" + inspection_mode = "detection" + ips_signature_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + log_level = "error" + custom_signature = false +} diff --git a/gen/definitions/profile_parcels/policy_object_unified_intrusion_prevention.yaml b/gen/definitions/profile_parcels/policy_object_unified_intrusion_prevention.yaml new file mode 100644 index 00000000..0654a333 --- /dev/null +++ b/gen/definitions/profile_parcels/policy_object_unified_intrusion_prevention.yaml @@ -0,0 +1,46 @@ +--- +name: Policy Object Unified Intrusion Prevention +rest_endpoint: /v1/feature-profile/sdwan/policy-object/%v/unified/intrusion-prevention +minimum_version: 20.12.0 +test_tags: [SDWAN_2012] +skip_minimum_test: true +parcel_type: policy_object +attributes: + - tf_name: feature_profile_id + reference: true + type: String + mandatory: true + description: Feature Profile ID + example: f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac + test_value: sdwan_policy_object_feature_profile.test.id + - model_name: signatureSet + example: balanced + - model_name: inspectionMode + example: detection + - model_name: refId + tf_name: ips_signature_list_id + data_path: [signatureAllowedList] + example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 + test_value: sdwan_policy_object_security_ips_signature.test.id + - model_name: logLevel + example: error + - model_name: customSignature + example: false + +test_prerequisites: | + resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" + } + + resource "sdwan_policy_object_security_ips_signature" "test" { + name = "Example" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + generator_id = "1234" + signature_id = "5678" + } + ] + } diff --git a/gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml b/gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml index d7f813b5..95325943 100644 --- a/gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml +++ b/gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml @@ -34,7 +34,6 @@ attributes: - model_name: blockPageContents example: Access to the requested page has been denied. Please contact your Network Administrator - model_name: redirectUrl - # exclude_test: true example: www.example.com - model_name: enableAlerts example: true diff --git a/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention.go b/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention.go new file mode 100644 index 00000000..87ef4d45 --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention.go @@ -0,0 +1,141 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/hashicorp/terraform-plugin-framework/datasource" + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure the implementation satisfies the expected interfaces. +var ( + _ datasource.DataSource = &PolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource{} + _ datasource.DataSourceWithConfigure = &PolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource{} +) + +func NewPolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource() datasource.DataSource { + return &PolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource{} +} + +type PolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource struct { + client *sdwan.Client +} + +func (d *PolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource) Metadata(_ context.Context, req datasource.MetadataRequest, resp *datasource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_intrusion_prevention" +} + +func (d *PolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource) Schema(ctx context.Context, req datasource.SchemaRequest, resp *datasource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: "This data source can read the Policy Object Unified Intrusion Prevention Policy_object.", + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Required: true, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Computed: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Computed: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: "Feature Profile ID", + Required: true, + }, + "signature_set": schema.StringAttribute{ + MarkdownDescription: "Can be one of the enum value", + Computed: true, + }, + "inspection_mode": schema.StringAttribute{ + MarkdownDescription: "Can be one of the enum value", + Computed: true, + }, + "ips_signature_list_id": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "log_level": schema.StringAttribute{ + MarkdownDescription: "Can be one of the enum value", + Computed: true, + }, + "custom_signature": schema.BoolAttribute{ + MarkdownDescription: "Can be one of the enum value", + Computed: true, + }, + }, + } +} + +func (d *PolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource) Configure(_ context.Context, req datasource.ConfigureRequest, _ *datasource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + d.client = req.ProviderData.(*SdwanProviderData).Client +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (d *PolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource) Read(ctx context.Context, req datasource.ReadRequest, resp *datasource.ReadResponse) { + var config PolicyObjectUnifiedIntrusionPrevention + + // Read config + diags := req.Config.Get(ctx, &config) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", config.Id.String())) + + res, err := d.client.Get(config.getPath() + "/" + url.QueryEscape(config.Id.ValueString())) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object, got error: %s", err)) + return + } + + config.fromBody(ctx, res) + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", config.Name.ValueString())) + + diags = resp.State.Set(ctx, &config) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read diff --git a/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention_test.go b/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention_test.go new file mode 100644 index 00000000..6da50085 --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention_test.go @@ -0,0 +1,99 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSource +func TestAccDataSourceSdwanPolicyObjectUnifiedIntrusionPreventionProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_intrusion_prevention.test", "signature_set", "balanced")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_intrusion_prevention.test", "inspection_mode", "detection")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_intrusion_prevention.test", "log_level", "error")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_intrusion_prevention.test", "custom_signature", "false")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + { + Config: testAccDataSourceSdwanPolicyObjectUnifiedIntrusionPreventionPrerequisitesProfileParcelConfig + testAccDataSourceSdwanPolicyObjectUnifiedIntrusionPreventionProfileParcelConfig(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAccDataSource + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccDataSourceSdwanPolicyObjectUnifiedIntrusionPreventionPrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} + +resource "sdwan_policy_object_security_ips_signature" "test" { + name = "Example" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + generator_id = "1234" + signature_id = "5678" + } + ] +} + +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSourceConfig +func testAccDataSourceSdwanPolicyObjectUnifiedIntrusionPreventionProfileParcelConfig() string { + config := `resource "sdwan_policy_object_unified_intrusion_prevention" "test" {` + "\n" + config += ` name = "TF_TEST"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` signature_set = "balanced"` + "\n" + config += ` inspection_mode = "detection"` + "\n" + config += ` ips_signature_list_id = sdwan_policy_object_security_ips_signature.test.id` + "\n" + config += ` log_level = "error"` + "\n" + config += ` custom_signature = false` + "\n" + config += `}` + "\n" + + config += ` + data "sdwan_policy_object_unified_intrusion_prevention" "test" { + id = sdwan_policy_object_unified_intrusion_prevention.test.id + feature_profile_id = sdwan_policy_object_feature_profile.test.id + } + ` + return config +} + +// End of section. //template:end testAccDataSourceConfig diff --git a/internal/provider/model_sdwan_policy_object_unified_intrusion_prevention.go b/internal/provider/model_sdwan_policy_object_unified_intrusion_prevention.go new file mode 100644 index 00000000..9d5c9599 --- /dev/null +++ b/internal/provider/model_sdwan_policy_object_unified_intrusion_prevention.go @@ -0,0 +1,233 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/tidwall/gjson" + "github.com/tidwall/sjson" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin types +type PolicyObjectUnifiedIntrusionPrevention struct { + Id types.String `tfsdk:"id"` + Version types.Int64 `tfsdk:"version"` + Name types.String `tfsdk:"name"` + Description types.String `tfsdk:"description"` + FeatureProfileId types.String `tfsdk:"feature_profile_id"` + SignatureSet types.String `tfsdk:"signature_set"` + InspectionMode types.String `tfsdk:"inspection_mode"` + IpsSignatureListId types.String `tfsdk:"ips_signature_list_id"` + LogLevel types.String `tfsdk:"log_level"` + CustomSignature types.Bool `tfsdk:"custom_signature"` +} + +// End of section. //template:end types + +// Section below is generated&owned by "gen/generator.go". //template:begin getModel +func (data PolicyObjectUnifiedIntrusionPrevention) getModel() string { + return "policy_object_unified_intrusion_prevention" +} + +// End of section. //template:end getModel + +// Section below is generated&owned by "gen/generator.go". //template:begin getPath +func (data PolicyObjectUnifiedIntrusionPrevention) getPath() string { + return fmt.Sprintf("/v1/feature-profile/sdwan/policy-object/%v/unified/intrusion-prevention", url.QueryEscape(data.FeatureProfileId.ValueString())) +} + +// End of section. //template:end getPath + +// Section below is generated&owned by "gen/generator.go". //template:begin toBody +func (data PolicyObjectUnifiedIntrusionPrevention) toBody(ctx context.Context) string { + body := "" + body, _ = sjson.Set(body, "name", data.Name.ValueString()) + body, _ = sjson.Set(body, "description", data.Description.ValueString()) + path := "data." + if !data.SignatureSet.IsNull() { + if true { + body, _ = sjson.Set(body, path+"signatureSet.optionType", "global") + body, _ = sjson.Set(body, path+"signatureSet.value", data.SignatureSet.ValueString()) + } + } + if !data.InspectionMode.IsNull() { + if true { + body, _ = sjson.Set(body, path+"inspectionMode.optionType", "global") + body, _ = sjson.Set(body, path+"inspectionMode.value", data.InspectionMode.ValueString()) + } + } + if !data.IpsSignatureListId.IsNull() { + if true { + body, _ = sjson.Set(body, path+"signatureAllowedList.refId.optionType", "global") + body, _ = sjson.Set(body, path+"signatureAllowedList.refId.value", data.IpsSignatureListId.ValueString()) + } + } + if !data.LogLevel.IsNull() { + if true { + body, _ = sjson.Set(body, path+"logLevel.optionType", "global") + body, _ = sjson.Set(body, path+"logLevel.value", data.LogLevel.ValueString()) + } + } + if !data.CustomSignature.IsNull() { + if true { + body, _ = sjson.Set(body, path+"customSignature.optionType", "global") + body, _ = sjson.Set(body, path+"customSignature.value", data.CustomSignature.ValueBool()) + } + } + return body +} + +// End of section. //template:end toBody + +// Section below is generated&owned by "gen/generator.go". //template:begin fromBody +func (data *PolicyObjectUnifiedIntrusionPrevention) fromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.SignatureSet = types.StringNull() + + if t := res.Get(path + "signatureSet.optionType"); t.Exists() { + va := res.Get(path + "signatureSet.value") + if t.String() == "global" { + data.SignatureSet = types.StringValue(va.String()) + } + } + data.InspectionMode = types.StringNull() + + if t := res.Get(path + "inspectionMode.optionType"); t.Exists() { + va := res.Get(path + "inspectionMode.value") + if t.String() == "global" { + data.InspectionMode = types.StringValue(va.String()) + } + } + data.IpsSignatureListId = types.StringNull() + + if t := res.Get(path + "signatureAllowedList.refId.optionType"); t.Exists() { + va := res.Get(path + "signatureAllowedList.refId.value") + if t.String() == "global" { + data.IpsSignatureListId = types.StringValue(va.String()) + } + } + data.LogLevel = types.StringNull() + + if t := res.Get(path + "logLevel.optionType"); t.Exists() { + va := res.Get(path + "logLevel.value") + if t.String() == "global" { + data.LogLevel = types.StringValue(va.String()) + } + } + data.CustomSignature = types.BoolNull() + + if t := res.Get(path + "customSignature.optionType"); t.Exists() { + va := res.Get(path + "customSignature.value") + if t.String() == "global" { + data.CustomSignature = types.BoolValue(va.Bool()) + } + } +} + +// End of section. //template:end fromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin updateFromBody +func (data *PolicyObjectUnifiedIntrusionPrevention) updateFromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.SignatureSet = types.StringNull() + + if t := res.Get(path + "signatureSet.optionType"); t.Exists() { + va := res.Get(path + "signatureSet.value") + if t.String() == "global" { + data.SignatureSet = types.StringValue(va.String()) + } + } + data.InspectionMode = types.StringNull() + + if t := res.Get(path + "inspectionMode.optionType"); t.Exists() { + va := res.Get(path + "inspectionMode.value") + if t.String() == "global" { + data.InspectionMode = types.StringValue(va.String()) + } + } + data.IpsSignatureListId = types.StringNull() + + if t := res.Get(path + "signatureAllowedList.refId.optionType"); t.Exists() { + va := res.Get(path + "signatureAllowedList.refId.value") + if t.String() == "global" { + data.IpsSignatureListId = types.StringValue(va.String()) + } + } + data.LogLevel = types.StringNull() + + if t := res.Get(path + "logLevel.optionType"); t.Exists() { + va := res.Get(path + "logLevel.value") + if t.String() == "global" { + data.LogLevel = types.StringValue(va.String()) + } + } + data.CustomSignature = types.BoolNull() + + if t := res.Get(path + "customSignature.optionType"); t.Exists() { + va := res.Get(path + "customSignature.value") + if t.String() == "global" { + data.CustomSignature = types.BoolValue(va.Bool()) + } + } +} + +// End of section. //template:end updateFromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin isNull +func (data *PolicyObjectUnifiedIntrusionPrevention) isNull(ctx context.Context, res gjson.Result) bool { + if !data.FeatureProfileId.IsNull() { + return false + } + if !data.SignatureSet.IsNull() { + return false + } + if !data.InspectionMode.IsNull() { + return false + } + if !data.IpsSignatureListId.IsNull() { + return false + } + if !data.LogLevel.IsNull() { + return false + } + if !data.CustomSignature.IsNull() { + return false + } + return true +} + +// End of section. //template:end isNull diff --git a/internal/provider/provider.go b/internal/provider/provider.go index bb570926..1ec974bd 100644 --- a/internal/provider/provider.go +++ b/internal/provider/provider.go @@ -314,6 +314,7 @@ func (p *SdwanProvider) Resources(ctx context.Context) []func() resource.Resourc NewPolicyObjectStandardCommunityListProfileParcelResource, NewPolicyObjectTLOCListProfileParcelResource, NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource, + NewPolicyObjectUnifiedIntrusionPreventionProfileParcelResource, NewPolicyObjectUnifiedTLSSSLProfileProfileParcelResource, NewPolicyObjectUnifiedURLFilteringProfileParcelResource, NewPolicyObjectVPNGroupProfileParcelResource, @@ -521,6 +522,7 @@ func (p *SdwanProvider) DataSources(ctx context.Context) []func() datasource.Dat NewPolicyObjectStandardCommunityListProfileParcelDataSource, NewPolicyObjectTLOCListProfileParcelDataSource, NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource, + NewPolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource, NewPolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource, NewPolicyObjectUnifiedURLFilteringProfileParcelDataSource, NewPolicyObjectVPNGroupProfileParcelDataSource, diff --git a/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention.go b/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention.go new file mode 100644 index 00000000..b92f9787 --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention.go @@ -0,0 +1,275 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + "regexp" + "sync" + + "github.com/CiscoDevNet/terraform-provider-sdwan/internal/provider/helpers" + "github.com/hashicorp/terraform-plugin-framework-validators/stringvalidator" + "github.com/hashicorp/terraform-plugin-framework/path" + "github.com/hashicorp/terraform-plugin-framework/resource" + "github.com/hashicorp/terraform-plugin-framework/resource/schema" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/planmodifier" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/stringplanmodifier" + "github.com/hashicorp/terraform-plugin-framework/schema/validator" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure provider defined types fully satisfy framework interfaces +var _ resource.Resource = &PolicyObjectUnifiedIntrusionPreventionProfileParcelResource{} +var _ resource.ResourceWithImportState = &PolicyObjectUnifiedIntrusionPreventionProfileParcelResource{} + +func NewPolicyObjectUnifiedIntrusionPreventionProfileParcelResource() resource.Resource { + return &PolicyObjectUnifiedIntrusionPreventionProfileParcelResource{} +} + +type PolicyObjectUnifiedIntrusionPreventionProfileParcelResource struct { + client *sdwan.Client + updateMutex *sync.Mutex +} + +func (r *PolicyObjectUnifiedIntrusionPreventionProfileParcelResource) Metadata(ctx context.Context, req resource.MetadataRequest, resp *resource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_intrusion_prevention" +} + +func (r *PolicyObjectUnifiedIntrusionPreventionProfileParcelResource) Schema(ctx context.Context, req resource.SchemaRequest, resp *resource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: helpers.NewAttributeDescription("This resource can manage a Policy Object Unified Intrusion Prevention Policy_object.").AddMinimumVersionDescription("20.12.0").String, + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Computed: true, + PlanModifiers: []planmodifier.String{ + stringplanmodifier.UseStateForUnknown(), + }, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Required: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Optional: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Feature Profile ID").String, + Required: true, + }, + "signature_set": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Can be one of the enum value").AddStringEnumDescription("balanced", "connectivity", "security").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("balanced", "connectivity", "security"), + }, + }, + "inspection_mode": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Can be one of the enum value").AddStringEnumDescription("detection", "protection").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("detection", "protection"), + }, + }, + "ips_signature_list_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + Validators: []validator.String{ + stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), + }, + }, + "log_level": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Can be one of the enum value").AddStringEnumDescription("emergency", "alert", "critical", "error", "warning", "notice", "info", "debug").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("emergency", "alert", "critical", "error", "warning", "notice", "info", "debug"), + }, + }, + "custom_signature": schema.BoolAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Can be one of the enum value").String, + Required: true, + }, + }, + } +} + +func (r *PolicyObjectUnifiedIntrusionPreventionProfileParcelResource) Configure(_ context.Context, req resource.ConfigureRequest, _ *resource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + r.client = req.ProviderData.(*SdwanProviderData).Client + r.updateMutex = req.ProviderData.(*SdwanProviderData).UpdateMutex +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin create +func (r *PolicyObjectUnifiedIntrusionPreventionProfileParcelResource) Create(ctx context.Context, req resource.CreateRequest, resp *resource.CreateResponse) { + var plan PolicyObjectUnifiedIntrusionPrevention + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Create", plan.Name.ValueString())) + + // Create object + body := plan.toBody(ctx) + + res, err := r.client.Post(plan.getPath(), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (POST), got error: %s, %s", err, res.String())) + return + } + + plan.Id = types.StringValue(res.Get("parcelId").String()) + plan.Version = types.Int64Value(0) + + tflog.Debug(ctx, fmt.Sprintf("%s: Create finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end create + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (r *PolicyObjectUnifiedIntrusionPreventionProfileParcelResource) Read(ctx context.Context, req resource.ReadRequest, resp *resource.ReadResponse) { + var state PolicyObjectUnifiedIntrusionPrevention + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", state.Name.String())) + + res, err := r.client.Get(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if res.Get("error.message").String() == "Invalid feature Id" { + resp.State.RemoveResource(ctx) + return + } else if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object (GET), got error: %s, %s", err, res.String())) + return + } + + // If every attribute is set to null we are dealing with an import operation and therefore reading all attributes + if state.isNull(ctx, res) { + state.fromBody(ctx, res) + } else { + state.updateFromBody(ctx, res) + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", state.Name.ValueString())) + + diags = resp.State.Set(ctx, &state) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read + +// Section below is generated&owned by "gen/generator.go". //template:begin update +func (r *PolicyObjectUnifiedIntrusionPreventionProfileParcelResource) Update(ctx context.Context, req resource.UpdateRequest, resp *resource.UpdateResponse) { + var plan, state PolicyObjectUnifiedIntrusionPrevention + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + // Read state + diags = req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Update", plan.Name.ValueString())) + + body := plan.toBody(ctx) + res, err := r.client.Put(plan.getPath()+"/"+url.QueryEscape(plan.Id.ValueString()), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (PUT), got error: %s, %s", err, res.String())) + return + } + + plan.Version = types.Int64Value(state.Version.ValueInt64() + 1) + + tflog.Debug(ctx, fmt.Sprintf("%s: Update finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end update + +// Section below is generated&owned by "gen/generator.go". //template:begin delete +func (r *PolicyObjectUnifiedIntrusionPreventionProfileParcelResource) Delete(ctx context.Context, req resource.DeleteRequest, resp *resource.DeleteResponse) { + var state PolicyObjectUnifiedIntrusionPrevention + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Delete", state.Name.ValueString())) + + res, err := r.client.Delete(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if err != nil && res.Get("error.message").String() != "Invalid Template Id" { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to delete object (DELETE), got error: %s, %s", err, res.String())) + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Delete finished successfully", state.Name.ValueString())) + + resp.State.RemoveResource(ctx) +} + +// End of section. //template:end delete + +// Section below is generated&owned by "gen/generator.go". //template:begin import +func (r *PolicyObjectUnifiedIntrusionPreventionProfileParcelResource) ImportState(ctx context.Context, req resource.ImportStateRequest, resp *resource.ImportStateResponse) { + resource.ImportStatePassthroughID(ctx, path.Root("id"), req, resp) +} + +// End of section. //template:end import diff --git a/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention_test.go b/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention_test.go new file mode 100644 index 00000000..c5da0b00 --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention_test.go @@ -0,0 +1,97 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAcc +func TestAccSdwanPolicyObjectUnifiedIntrusionPreventionProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_intrusion_prevention.test", "signature_set", "balanced")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_intrusion_prevention.test", "inspection_mode", "detection")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_intrusion_prevention.test", "log_level", "error")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_intrusion_prevention.test", "custom_signature", "false")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + + { + Config: testAccSdwanPolicyObjectUnifiedIntrusionPreventionPrerequisitesProfileParcelConfig + testAccSdwanPolicyObjectUnifiedIntrusionPreventionProfileParcelConfig_all(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAcc + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccSdwanPolicyObjectUnifiedIntrusionPreventionPrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} + +resource "sdwan_policy_object_security_ips_signature" "test" { + name = "Example" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + generator_id = "1234" + signature_id = "5678" + } + ] +} + +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigMinimum + +// End of section. //template:end testAccConfigMinimum + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigAll +func testAccSdwanPolicyObjectUnifiedIntrusionPreventionProfileParcelConfig_all() string { + config := `resource "sdwan_policy_object_unified_intrusion_prevention" "test" {` + "\n" + config += ` name = "TF_TEST_ALL"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` signature_set = "balanced"` + "\n" + config += ` inspection_mode = "detection"` + "\n" + config += ` ips_signature_list_id = sdwan_policy_object_security_ips_signature.test.id` + "\n" + config += ` log_level = "error"` + "\n" + config += ` custom_signature = false` + "\n" + config += `}` + "\n" + return config +} + +// End of section. //template:end testAccConfigAll diff --git a/templates/guides/changelog.md.tmpl b/templates/guides/changelog.md.tmpl index 8fb73474..27544a70 100644 --- a/templates/guides/changelog.md.tmpl +++ b/templates/guides/changelog.md.tmpl @@ -37,6 +37,7 @@ description: |- - Add `sdwan_policy_object_unified_advanced_malware_protection` resource and data source - Add `sdwan_policy_object_unified_url_filtering` resource and data source - Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source +- Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source ## 0.4.1 From 1c66ad358b8303cb959cbd6484d0790ef5f33381 Mon Sep 17 00:00:00 2001 From: Sean Conroy Date: Fri, 13 Sep 2024 17:09:47 +0100 Subject: [PATCH 06/11] Add policy object unified advanced inspection profile resource and data source --- CHANGELOG.md | 1 + ...ect_unified_advanced_inspection_profile.md | 39 +++ docs/guides/changelog.md | 1 + ...ect_unified_advanced_inspection_profile.md | 58 ++++ .../data-source.tf | 4 + .../import.sh | 1 + .../resource.tf | 10 + ...t_unified_advanced_inspection_profile.yaml | 133 +++++++++ ...ect_unified_advanced_inspection_profile.go | 141 +++++++++ ...nified_advanced_inspection_profile_test.go | 173 +++++++++++ ...ect_unified_advanced_inspection_profile.go | 233 +++++++++++++++ internal/provider/provider.go | 2 + ...ect_unified_advanced_inspection_profile.go | 278 ++++++++++++++++++ ...nified_advanced_inspection_profile_test.go | 171 +++++++++++ templates/guides/changelog.md.tmpl | 1 + 15 files changed, 1246 insertions(+) create mode 100644 docs/data-sources/policy_object_unified_advanced_inspection_profile.md create mode 100644 docs/resources/policy_object_unified_advanced_inspection_profile.md create mode 100644 examples/data-sources/sdwan_policy_object_unified_advanced_inspection_profile/data-source.tf create mode 100644 examples/resources/sdwan_policy_object_unified_advanced_inspection_profile/import.sh create mode 100644 examples/resources/sdwan_policy_object_unified_advanced_inspection_profile/resource.tf create mode 100644 gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile.go create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go create mode 100644 internal/provider/model_sdwan_policy_object_unified_advanced_inspection_profile.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go diff --git a/CHANGELOG.md b/CHANGELOG.md index 7b4f7c6e..903bacd2 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -29,6 +29,7 @@ - Add `sdwan_policy_object_unified_url_filtering` resource and data source - Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source - Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source +- Add `sdwan_policy_object_unified_advanced_inspection_profile` resource and data source ## 0.4.1 diff --git a/docs/data-sources/policy_object_unified_advanced_inspection_profile.md b/docs/data-sources/policy_object_unified_advanced_inspection_profile.md new file mode 100644 index 00000000..4a71c85b --- /dev/null +++ b/docs/data-sources/policy_object_unified_advanced_inspection_profile.md @@ -0,0 +1,39 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_advanced_inspection_profile Data Source - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This data source can read the Policy Object Unified Advanced Inspection Profile Policy_object. +--- + +# sdwan_policy_object_unified_advanced_inspection_profile (Data Source) + +This data source can read the Policy Object Unified Advanced Inspection Profile Policy_object. + +## Example Usage + +```terraform +data "sdwan_policy_object_unified_advanced_inspection_profile" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} +``` + + +## Schema + +### Required + +- `feature_profile_id` (String) Feature Profile ID +- `id` (String) The id of the Policy_object + +### Read-Only + +- `advanced_malware_protection_list_id` (String) +- `description` (String) The description of the Policy_object +- `intrusion_prevention_list_id` (String) +- `name` (String) The name of the Policy_object +- `tls_decryption_action` (String) +- `tls_ssl_profile_list_id` (String) +- `url_filtering_list_id` (String) +- `version` (Number) The version of the Policy_object diff --git a/docs/guides/changelog.md b/docs/guides/changelog.md index 27544a70..e037a473 100644 --- a/docs/guides/changelog.md +++ b/docs/guides/changelog.md @@ -38,6 +38,7 @@ description: |- - Add `sdwan_policy_object_unified_url_filtering` resource and data source - Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source - Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source +- Add `sdwan_policy_object_unified_advanced_inspection_profile` resource and data source ## 0.4.1 diff --git a/docs/resources/policy_object_unified_advanced_inspection_profile.md b/docs/resources/policy_object_unified_advanced_inspection_profile.md new file mode 100644 index 00000000..bc0e803f --- /dev/null +++ b/docs/resources/policy_object_unified_advanced_inspection_profile.md @@ -0,0 +1,58 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_advanced_inspection_profile Resource - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This resource can manage a Policy Object Unified Advanced Inspection Profile Policy_object. + Minimum SD-WAN Manager version: 20.12.0 +--- + +# sdwan_policy_object_unified_advanced_inspection_profile (Resource) + +This resource can manage a Policy Object Unified Advanced Inspection Profile Policy_object. + - Minimum SD-WAN Manager version: `20.12.0` + +## Example Usage + +```terraform +resource "sdwan_policy_object_unified_advanced_inspection_profile" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + tls_decryption_action = "decrypt" + intrusion_prevention_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + url_filtering_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + advanced_malware_protection_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + tls_ssl_profile_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" +} +``` + + +## Schema + +### Required + +- `advanced_malware_protection_list_id` (String) +- `feature_profile_id` (String) Feature Profile ID +- `intrusion_prevention_list_id` (String) +- `name` (String) The name of the Policy_object +- `tls_decryption_action` (String) - Choices: `decrypt`, `neverDecrypt`, `skipDecrypt` +- `tls_ssl_profile_list_id` (String) +- `url_filtering_list_id` (String) + +### Optional + +- `description` (String) The description of the Policy_object + +### Read-Only + +- `id` (String) The id of the Policy_object +- `version` (Number) The version of the Policy_object + +## Import + +Import is supported using the following syntax: + +```shell +terraform import sdwan_policy_object_unified_advanced_inspection_profile.example "f6b2c44c-693c-4763-b010-895aa3d236bd" +``` diff --git a/examples/data-sources/sdwan_policy_object_unified_advanced_inspection_profile/data-source.tf b/examples/data-sources/sdwan_policy_object_unified_advanced_inspection_profile/data-source.tf new file mode 100644 index 00000000..7ac784e8 --- /dev/null +++ b/examples/data-sources/sdwan_policy_object_unified_advanced_inspection_profile/data-source.tf @@ -0,0 +1,4 @@ +data "sdwan_policy_object_unified_advanced_inspection_profile" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} diff --git a/examples/resources/sdwan_policy_object_unified_advanced_inspection_profile/import.sh b/examples/resources/sdwan_policy_object_unified_advanced_inspection_profile/import.sh new file mode 100644 index 00000000..2d5791eb --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_advanced_inspection_profile/import.sh @@ -0,0 +1 @@ +terraform import sdwan_policy_object_unified_advanced_inspection_profile.example "f6b2c44c-693c-4763-b010-895aa3d236bd" diff --git a/examples/resources/sdwan_policy_object_unified_advanced_inspection_profile/resource.tf b/examples/resources/sdwan_policy_object_unified_advanced_inspection_profile/resource.tf new file mode 100644 index 00000000..80c39f63 --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_advanced_inspection_profile/resource.tf @@ -0,0 +1,10 @@ +resource "sdwan_policy_object_unified_advanced_inspection_profile" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + tls_decryption_action = "decrypt" + intrusion_prevention_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + url_filtering_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + advanced_malware_protection_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + tls_ssl_profile_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" +} diff --git a/gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml b/gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml new file mode 100644 index 00000000..b8065cf9 --- /dev/null +++ b/gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml @@ -0,0 +1,133 @@ +--- +name: Policy Object Unified Advanced Inspection Profile +rest_endpoint: /v1/feature-profile/sdwan/policy-object/%v/unified/advanced-inspection-profile +minimum_version: 20.12.0 +test_tags: [SDWAN_2012] +skip_minimum_test: true +parcel_type: policy_object +attributes: + - tf_name: feature_profile_id + reference: true + type: String + mandatory: true + description: Feature Profile ID + example: f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac + test_value: sdwan_policy_object_feature_profile.test.id + - model_name: tlsDecryptionAction + example: decrypt + - model_name: refId + tf_name: intrusion_prevention_list_id + data_path: [intrusionPrevention] + example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 + test_value: sdwan_policy_object_unified_intrusion_prevention.test.id + - model_name: refId + tf_name: url_filtering_list_id + data_path: [urlFiltering] + example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 + test_value: sdwan_policy_object_security_url_allow_list.test.id + - model_name: refId + tf_name: advanced_malware_protection_list_id + data_path: [advancedMalwareProtection] + example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 + test_value: sdwan_policy_object_unified_advanced_malware_protection.test.id + - model_name: refId + tf_name: tls_ssl_profile_list_id + data_path: [sslDecryptionProfile] + example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 + test_value: sdwan_policy_object_unified_tls_ssl_profile.test.id + +test_prerequisites: | + resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" + } + + resource "sdwan_policy_object_security_url_allow_list" "test" { + name = "TF_TEST_ALLOW" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] + } + + resource "sdwan_policy_object_security_url_block_list" "test" { + name = "TF_TEST_BLOCK" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] + } + + resource "sdwan_policy_object_unified_url_filtering" "test" { + name = "TF_TEST_URL_FILTERING" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + web_categories_action = "block" + web_categories = ["confirmed-spam-sources"] + web_reputation = "suspicious" + url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id + url_block_list_id = sdwan_policy_object_security_url_block_list.test.id + block_page_action = "text" + block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator" + redirect_url = "www.example.com" + enable_alerts = true + alerts = ["blacklist"] + } + + resource "sdwan_policy_object_security_ips_signature" "test" { + name = "Example" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + generator_id = "1234" + signature_id = "5678" + } + ] + } + + resource "sdwan_policy_object_unified_intrusion_prevention" "test" { + name = "TF_TEST_INTRUSION" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + signature_set = "balanced" + inspection_mode = "detection" + ips_signature_list_id = sdwan_policy_object_security_ips_signature.test.id + log_level = "error" + custom_signature = false + } + + resource "sdwan_policy_object_unified_advanced_malware_protection" "test" { + name = "TF_TEST_ADVANCED_MALWARE" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + match_all_vpn = true + amp_cloud_region = "nam" + amp_cloud_region_est_server = "nam" + alert_log_level = "critical" + file_analysis = true + file_analysis_cloud_region = "nam" + file_analysis_file_types = ["pdf"] + file_analysis_alert_log_level = "critical" + } + + resource "sdwan_policy_object_unified_tls_ssl_profile" "test" { + name = "TF_TEST_TLS_SSL_PROFILE" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + decrypt_categories = ["alcohol-and-tobacco"] + no_decrypt_categories = ["abortion"] + pass_through_categories = ["auctions"] + reputation = true + decrypt_threshold = "moderate-risk" + threshold_categories = "moderate-risk" + fail_decrypt = true + url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id + url_block_list_id = sdwan_policy_object_security_url_block_list.test.id + } \ No newline at end of file diff --git a/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile.go b/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile.go new file mode 100644 index 00000000..b3908c24 --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile.go @@ -0,0 +1,141 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/hashicorp/terraform-plugin-framework/datasource" + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure the implementation satisfies the expected interfaces. +var ( + _ datasource.DataSource = &PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelDataSource{} + _ datasource.DataSourceWithConfigure = &PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelDataSource{} +) + +func NewPolicyObjectUnifiedAdvancedInspectionProfileProfileParcelDataSource() datasource.DataSource { + return &PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelDataSource{} +} + +type PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelDataSource struct { + client *sdwan.Client +} + +func (d *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelDataSource) Metadata(_ context.Context, req datasource.MetadataRequest, resp *datasource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_advanced_inspection_profile" +} + +func (d *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelDataSource) Schema(ctx context.Context, req datasource.SchemaRequest, resp *datasource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: "This data source can read the Policy Object Unified Advanced Inspection Profile Policy_object.", + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Required: true, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Computed: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Computed: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: "Feature Profile ID", + Required: true, + }, + "tls_decryption_action": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "intrusion_prevention_list_id": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "url_filtering_list_id": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "advanced_malware_protection_list_id": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "tls_ssl_profile_list_id": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + }, + } +} + +func (d *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelDataSource) Configure(_ context.Context, req datasource.ConfigureRequest, _ *datasource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + d.client = req.ProviderData.(*SdwanProviderData).Client +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (d *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelDataSource) Read(ctx context.Context, req datasource.ReadRequest, resp *datasource.ReadResponse) { + var config PolicyObjectUnifiedAdvancedInspectionProfile + + // Read config + diags := req.Config.Get(ctx, &config) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", config.Id.String())) + + res, err := d.client.Get(config.getPath() + "/" + url.QueryEscape(config.Id.ValueString())) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object, got error: %s", err)) + return + } + + config.fromBody(ctx, res) + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", config.Name.ValueString())) + + diags = resp.State.Set(ctx, &config) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read diff --git a/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go b/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go new file mode 100644 index 00000000..559fcaea --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go @@ -0,0 +1,173 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSource +func TestAccDataSourceSdwanPolicyObjectUnifiedAdvancedInspectionProfileProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_inspection_profile.test", "tls_decryption_action", "decrypt")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + { + Config: testAccDataSourceSdwanPolicyObjectUnifiedAdvancedInspectionProfilePrerequisitesProfileParcelConfig + testAccDataSourceSdwanPolicyObjectUnifiedAdvancedInspectionProfileProfileParcelConfig(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAccDataSource + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccDataSourceSdwanPolicyObjectUnifiedAdvancedInspectionProfilePrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} + +resource "sdwan_policy_object_security_url_allow_list" "test" { + name = "TF_TEST_ALLOW" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} + +resource "sdwan_policy_object_security_url_block_list" "test" { + name = "TF_TEST_BLOCK" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} + +resource "sdwan_policy_object_unified_url_filtering" "test" { + name = "TF_TEST_URL_FILTERING" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + web_categories_action = "block" + web_categories = ["confirmed-spam-sources"] + web_reputation = "suspicious" + url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id + url_block_list_id = sdwan_policy_object_security_url_block_list.test.id + block_page_action = "text" + block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator" + redirect_url = "www.example.com" + enable_alerts = true + alerts = ["blacklist"] +} + +resource "sdwan_policy_object_security_ips_signature" "test" { + name = "Example" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + generator_id = "1234" + signature_id = "5678" + } + ] +} + +resource "sdwan_policy_object_unified_intrusion_prevention" "test" { + name = "TF_TEST_INTRUSION" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + signature_set = "balanced" + inspection_mode = "detection" + ips_signature_list_id = sdwan_policy_object_security_ips_signature.test.id + log_level = "error" + custom_signature = false +} + +resource "sdwan_policy_object_unified_advanced_malware_protection" "test" { + name = "TF_TEST_ADVANCED_MALWARE" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + match_all_vpn = true + amp_cloud_region = "nam" + amp_cloud_region_est_server = "nam" + alert_log_level = "critical" + file_analysis = true + file_analysis_cloud_region = "nam" + file_analysis_file_types = ["pdf"] + file_analysis_alert_log_level = "critical" +} + +resource "sdwan_policy_object_unified_tls_ssl_profile" "test" { + name = "TF_TEST_TLS_SSL_PROFILE" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + decrypt_categories = ["alcohol-and-tobacco"] + no_decrypt_categories = ["abortion"] + pass_through_categories = ["auctions"] + reputation = true + decrypt_threshold = "moderate-risk" + threshold_categories = "moderate-risk" + fail_decrypt = true + url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id + url_block_list_id = sdwan_policy_object_security_url_block_list.test.id +} +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSourceConfig +func testAccDataSourceSdwanPolicyObjectUnifiedAdvancedInspectionProfileProfileParcelConfig() string { + config := `resource "sdwan_policy_object_unified_advanced_inspection_profile" "test" {` + "\n" + config += ` name = "TF_TEST"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` tls_decryption_action = "decrypt"` + "\n" + config += ` intrusion_prevention_list_id = sdwan_policy_object_unified_intrusion_prevention.test.id` + "\n" + config += ` url_filtering_list_id = sdwan_policy_object_security_url_allow_list.test.id` + "\n" + config += ` advanced_malware_protection_list_id = sdwan_policy_object_unified_advanced_malware_protection.test.id` + "\n" + config += ` tls_ssl_profile_list_id = sdwan_policy_object_unified_tls_ssl_profile.test.id` + "\n" + config += `}` + "\n" + + config += ` + data "sdwan_policy_object_unified_advanced_inspection_profile" "test" { + id = sdwan_policy_object_unified_advanced_inspection_profile.test.id + feature_profile_id = sdwan_policy_object_feature_profile.test.id + } + ` + return config +} + +// End of section. //template:end testAccDataSourceConfig diff --git a/internal/provider/model_sdwan_policy_object_unified_advanced_inspection_profile.go b/internal/provider/model_sdwan_policy_object_unified_advanced_inspection_profile.go new file mode 100644 index 00000000..f8834855 --- /dev/null +++ b/internal/provider/model_sdwan_policy_object_unified_advanced_inspection_profile.go @@ -0,0 +1,233 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/tidwall/gjson" + "github.com/tidwall/sjson" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin types +type PolicyObjectUnifiedAdvancedInspectionProfile struct { + Id types.String `tfsdk:"id"` + Version types.Int64 `tfsdk:"version"` + Name types.String `tfsdk:"name"` + Description types.String `tfsdk:"description"` + FeatureProfileId types.String `tfsdk:"feature_profile_id"` + TlsDecryptionAction types.String `tfsdk:"tls_decryption_action"` + IntrusionPreventionListId types.String `tfsdk:"intrusion_prevention_list_id"` + UrlFilteringListId types.String `tfsdk:"url_filtering_list_id"` + AdvancedMalwareProtectionListId types.String `tfsdk:"advanced_malware_protection_list_id"` + TlsSslProfileListId types.String `tfsdk:"tls_ssl_profile_list_id"` +} + +// End of section. //template:end types + +// Section below is generated&owned by "gen/generator.go". //template:begin getModel +func (data PolicyObjectUnifiedAdvancedInspectionProfile) getModel() string { + return "policy_object_unified_advanced_inspection_profile" +} + +// End of section. //template:end getModel + +// Section below is generated&owned by "gen/generator.go". //template:begin getPath +func (data PolicyObjectUnifiedAdvancedInspectionProfile) getPath() string { + return fmt.Sprintf("/v1/feature-profile/sdwan/policy-object/%v/unified/advanced-inspection-profile", url.QueryEscape(data.FeatureProfileId.ValueString())) +} + +// End of section. //template:end getPath + +// Section below is generated&owned by "gen/generator.go". //template:begin toBody +func (data PolicyObjectUnifiedAdvancedInspectionProfile) toBody(ctx context.Context) string { + body := "" + body, _ = sjson.Set(body, "name", data.Name.ValueString()) + body, _ = sjson.Set(body, "description", data.Description.ValueString()) + path := "data." + if !data.TlsDecryptionAction.IsNull() { + if true { + body, _ = sjson.Set(body, path+"tlsDecryptionAction.optionType", "global") + body, _ = sjson.Set(body, path+"tlsDecryptionAction.value", data.TlsDecryptionAction.ValueString()) + } + } + if !data.IntrusionPreventionListId.IsNull() { + if true { + body, _ = sjson.Set(body, path+"intrusionPrevention.refId.optionType", "global") + body, _ = sjson.Set(body, path+"intrusionPrevention.refId.value", data.IntrusionPreventionListId.ValueString()) + } + } + if !data.UrlFilteringListId.IsNull() { + if true { + body, _ = sjson.Set(body, path+"urlFiltering.refId.optionType", "global") + body, _ = sjson.Set(body, path+"urlFiltering.refId.value", data.UrlFilteringListId.ValueString()) + } + } + if !data.AdvancedMalwareProtectionListId.IsNull() { + if true { + body, _ = sjson.Set(body, path+"advancedMalwareProtection.refId.optionType", "global") + body, _ = sjson.Set(body, path+"advancedMalwareProtection.refId.value", data.AdvancedMalwareProtectionListId.ValueString()) + } + } + if !data.TlsSslProfileListId.IsNull() { + if true { + body, _ = sjson.Set(body, path+"sslDecryptionProfile.refId.optionType", "global") + body, _ = sjson.Set(body, path+"sslDecryptionProfile.refId.value", data.TlsSslProfileListId.ValueString()) + } + } + return body +} + +// End of section. //template:end toBody + +// Section below is generated&owned by "gen/generator.go". //template:begin fromBody +func (data *PolicyObjectUnifiedAdvancedInspectionProfile) fromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.TlsDecryptionAction = types.StringNull() + + if t := res.Get(path + "tlsDecryptionAction.optionType"); t.Exists() { + va := res.Get(path + "tlsDecryptionAction.value") + if t.String() == "global" { + data.TlsDecryptionAction = types.StringValue(va.String()) + } + } + data.IntrusionPreventionListId = types.StringNull() + + if t := res.Get(path + "intrusionPrevention.refId.optionType"); t.Exists() { + va := res.Get(path + "intrusionPrevention.refId.value") + if t.String() == "global" { + data.IntrusionPreventionListId = types.StringValue(va.String()) + } + } + data.UrlFilteringListId = types.StringNull() + + if t := res.Get(path + "urlFiltering.refId.optionType"); t.Exists() { + va := res.Get(path + "urlFiltering.refId.value") + if t.String() == "global" { + data.UrlFilteringListId = types.StringValue(va.String()) + } + } + data.AdvancedMalwareProtectionListId = types.StringNull() + + if t := res.Get(path + "advancedMalwareProtection.refId.optionType"); t.Exists() { + va := res.Get(path + "advancedMalwareProtection.refId.value") + if t.String() == "global" { + data.AdvancedMalwareProtectionListId = types.StringValue(va.String()) + } + } + data.TlsSslProfileListId = types.StringNull() + + if t := res.Get(path + "sslDecryptionProfile.refId.optionType"); t.Exists() { + va := res.Get(path + "sslDecryptionProfile.refId.value") + if t.String() == "global" { + data.TlsSslProfileListId = types.StringValue(va.String()) + } + } +} + +// End of section. //template:end fromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin updateFromBody +func (data *PolicyObjectUnifiedAdvancedInspectionProfile) updateFromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.TlsDecryptionAction = types.StringNull() + + if t := res.Get(path + "tlsDecryptionAction.optionType"); t.Exists() { + va := res.Get(path + "tlsDecryptionAction.value") + if t.String() == "global" { + data.TlsDecryptionAction = types.StringValue(va.String()) + } + } + data.IntrusionPreventionListId = types.StringNull() + + if t := res.Get(path + "intrusionPrevention.refId.optionType"); t.Exists() { + va := res.Get(path + "intrusionPrevention.refId.value") + if t.String() == "global" { + data.IntrusionPreventionListId = types.StringValue(va.String()) + } + } + data.UrlFilteringListId = types.StringNull() + + if t := res.Get(path + "urlFiltering.refId.optionType"); t.Exists() { + va := res.Get(path + "urlFiltering.refId.value") + if t.String() == "global" { + data.UrlFilteringListId = types.StringValue(va.String()) + } + } + data.AdvancedMalwareProtectionListId = types.StringNull() + + if t := res.Get(path + "advancedMalwareProtection.refId.optionType"); t.Exists() { + va := res.Get(path + "advancedMalwareProtection.refId.value") + if t.String() == "global" { + data.AdvancedMalwareProtectionListId = types.StringValue(va.String()) + } + } + data.TlsSslProfileListId = types.StringNull() + + if t := res.Get(path + "sslDecryptionProfile.refId.optionType"); t.Exists() { + va := res.Get(path + "sslDecryptionProfile.refId.value") + if t.String() == "global" { + data.TlsSslProfileListId = types.StringValue(va.String()) + } + } +} + +// End of section. //template:end updateFromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin isNull +func (data *PolicyObjectUnifiedAdvancedInspectionProfile) isNull(ctx context.Context, res gjson.Result) bool { + if !data.FeatureProfileId.IsNull() { + return false + } + if !data.TlsDecryptionAction.IsNull() { + return false + } + if !data.IntrusionPreventionListId.IsNull() { + return false + } + if !data.UrlFilteringListId.IsNull() { + return false + } + if !data.AdvancedMalwareProtectionListId.IsNull() { + return false + } + if !data.TlsSslProfileListId.IsNull() { + return false + } + return true +} + +// End of section. //template:end isNull diff --git a/internal/provider/provider.go b/internal/provider/provider.go index 1ec974bd..ef9ff171 100644 --- a/internal/provider/provider.go +++ b/internal/provider/provider.go @@ -313,6 +313,7 @@ func (p *SdwanProvider) Resources(ctx context.Context) []func() resource.Resourc NewPolicyObjectSLAClassListProfileParcelResource, NewPolicyObjectStandardCommunityListProfileParcelResource, NewPolicyObjectTLOCListProfileParcelResource, + NewPolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource, NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource, NewPolicyObjectUnifiedIntrusionPreventionProfileParcelResource, NewPolicyObjectUnifiedTLSSSLProfileProfileParcelResource, @@ -521,6 +522,7 @@ func (p *SdwanProvider) DataSources(ctx context.Context) []func() datasource.Dat NewPolicyObjectSLAClassListProfileParcelDataSource, NewPolicyObjectStandardCommunityListProfileParcelDataSource, NewPolicyObjectTLOCListProfileParcelDataSource, + NewPolicyObjectUnifiedAdvancedInspectionProfileProfileParcelDataSource, NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource, NewPolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource, NewPolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource, diff --git a/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile.go b/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile.go new file mode 100644 index 00000000..06884f1a --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile.go @@ -0,0 +1,278 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + "regexp" + "sync" + + "github.com/CiscoDevNet/terraform-provider-sdwan/internal/provider/helpers" + "github.com/hashicorp/terraform-plugin-framework-validators/stringvalidator" + "github.com/hashicorp/terraform-plugin-framework/path" + "github.com/hashicorp/terraform-plugin-framework/resource" + "github.com/hashicorp/terraform-plugin-framework/resource/schema" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/planmodifier" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/stringplanmodifier" + "github.com/hashicorp/terraform-plugin-framework/schema/validator" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure provider defined types fully satisfy framework interfaces +var _ resource.Resource = &PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource{} +var _ resource.ResourceWithImportState = &PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource{} + +func NewPolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource() resource.Resource { + return &PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource{} +} + +type PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource struct { + client *sdwan.Client + updateMutex *sync.Mutex +} + +func (r *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource) Metadata(ctx context.Context, req resource.MetadataRequest, resp *resource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_advanced_inspection_profile" +} + +func (r *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource) Schema(ctx context.Context, req resource.SchemaRequest, resp *resource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: helpers.NewAttributeDescription("This resource can manage a Policy Object Unified Advanced Inspection Profile Policy_object.").AddMinimumVersionDescription("20.12.0").String, + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Computed: true, + PlanModifiers: []planmodifier.String{ + stringplanmodifier.UseStateForUnknown(), + }, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Required: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Optional: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Feature Profile ID").String, + Required: true, + }, + "tls_decryption_action": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("decrypt", "neverDecrypt", "skipDecrypt").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("decrypt", "neverDecrypt", "skipDecrypt"), + }, + }, + "intrusion_prevention_list_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + Validators: []validator.String{ + stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), + }, + }, + "url_filtering_list_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + Validators: []validator.String{ + stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), + }, + }, + "advanced_malware_protection_list_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + Validators: []validator.String{ + stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), + }, + }, + "tls_ssl_profile_list_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + Validators: []validator.String{ + stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), + }, + }, + }, + } +} + +func (r *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource) Configure(_ context.Context, req resource.ConfigureRequest, _ *resource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + r.client = req.ProviderData.(*SdwanProviderData).Client + r.updateMutex = req.ProviderData.(*SdwanProviderData).UpdateMutex +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin create +func (r *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource) Create(ctx context.Context, req resource.CreateRequest, resp *resource.CreateResponse) { + var plan PolicyObjectUnifiedAdvancedInspectionProfile + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Create", plan.Name.ValueString())) + + // Create object + body := plan.toBody(ctx) + + res, err := r.client.Post(plan.getPath(), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (POST), got error: %s, %s", err, res.String())) + return + } + + plan.Id = types.StringValue(res.Get("parcelId").String()) + plan.Version = types.Int64Value(0) + + tflog.Debug(ctx, fmt.Sprintf("%s: Create finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end create + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (r *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource) Read(ctx context.Context, req resource.ReadRequest, resp *resource.ReadResponse) { + var state PolicyObjectUnifiedAdvancedInspectionProfile + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", state.Name.String())) + + res, err := r.client.Get(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if res.Get("error.message").String() == "Invalid feature Id" { + resp.State.RemoveResource(ctx) + return + } else if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object (GET), got error: %s, %s", err, res.String())) + return + } + + // If every attribute is set to null we are dealing with an import operation and therefore reading all attributes + if state.isNull(ctx, res) { + state.fromBody(ctx, res) + } else { + state.updateFromBody(ctx, res) + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", state.Name.ValueString())) + + diags = resp.State.Set(ctx, &state) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read + +// Section below is generated&owned by "gen/generator.go". //template:begin update +func (r *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource) Update(ctx context.Context, req resource.UpdateRequest, resp *resource.UpdateResponse) { + var plan, state PolicyObjectUnifiedAdvancedInspectionProfile + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + // Read state + diags = req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Update", plan.Name.ValueString())) + + body := plan.toBody(ctx) + res, err := r.client.Put(plan.getPath()+"/"+url.QueryEscape(plan.Id.ValueString()), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (PUT), got error: %s, %s", err, res.String())) + return + } + + plan.Version = types.Int64Value(state.Version.ValueInt64() + 1) + + tflog.Debug(ctx, fmt.Sprintf("%s: Update finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end update + +// Section below is generated&owned by "gen/generator.go". //template:begin delete +func (r *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource) Delete(ctx context.Context, req resource.DeleteRequest, resp *resource.DeleteResponse) { + var state PolicyObjectUnifiedAdvancedInspectionProfile + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Delete", state.Name.ValueString())) + + res, err := r.client.Delete(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if err != nil && res.Get("error.message").String() != "Invalid Template Id" { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to delete object (DELETE), got error: %s, %s", err, res.String())) + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Delete finished successfully", state.Name.ValueString())) + + resp.State.RemoveResource(ctx) +} + +// End of section. //template:end delete + +// Section below is generated&owned by "gen/generator.go". //template:begin import +func (r *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource) ImportState(ctx context.Context, req resource.ImportStateRequest, resp *resource.ImportStateResponse) { + resource.ImportStatePassthroughID(ctx, path.Root("id"), req, resp) +} + +// End of section. //template:end import diff --git a/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go b/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go new file mode 100644 index 00000000..3f1e7da1 --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go @@ -0,0 +1,171 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAcc +func TestAccSdwanPolicyObjectUnifiedAdvancedInspectionProfileProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_inspection_profile.test", "tls_decryption_action", "decrypt")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + + { + Config: testAccSdwanPolicyObjectUnifiedAdvancedInspectionProfilePrerequisitesProfileParcelConfig + testAccSdwanPolicyObjectUnifiedAdvancedInspectionProfileProfileParcelConfig_all(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAcc + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccSdwanPolicyObjectUnifiedAdvancedInspectionProfilePrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} + +resource "sdwan_policy_object_security_url_allow_list" "test" { + name = "TF_TEST_ALLOW" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} + +resource "sdwan_policy_object_security_url_block_list" "test" { + name = "TF_TEST_BLOCK" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + pattern = "www.cisco.com" + } + ] +} + +resource "sdwan_policy_object_unified_url_filtering" "test" { + name = "TF_TEST_URL_FILTERING" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + web_categories_action = "block" + web_categories = ["confirmed-spam-sources"] + web_reputation = "suspicious" + url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id + url_block_list_id = sdwan_policy_object_security_url_block_list.test.id + block_page_action = "text" + block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator" + redirect_url = "www.example.com" + enable_alerts = true + alerts = ["blacklist"] +} + +resource "sdwan_policy_object_security_ips_signature" "test" { + name = "Example" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + entries = [ + { + generator_id = "1234" + signature_id = "5678" + } + ] +} + +resource "sdwan_policy_object_unified_intrusion_prevention" "test" { + name = "TF_TEST_INTRUSION" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + signature_set = "balanced" + inspection_mode = "detection" + ips_signature_list_id = sdwan_policy_object_security_ips_signature.test.id + log_level = "error" + custom_signature = false +} + +resource "sdwan_policy_object_unified_advanced_malware_protection" "test" { + name = "TF_TEST_ADVANCED_MALWARE" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + match_all_vpn = true + amp_cloud_region = "nam" + amp_cloud_region_est_server = "nam" + alert_log_level = "critical" + file_analysis = true + file_analysis_cloud_region = "nam" + file_analysis_file_types = ["pdf"] + file_analysis_alert_log_level = "critical" +} + +resource "sdwan_policy_object_unified_tls_ssl_profile" "test" { + name = "TF_TEST_TLS_SSL_PROFILE" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + decrypt_categories = ["alcohol-and-tobacco"] + no_decrypt_categories = ["abortion"] + pass_through_categories = ["auctions"] + reputation = true + decrypt_threshold = "moderate-risk" + threshold_categories = "moderate-risk" + fail_decrypt = true + url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id + url_block_list_id = sdwan_policy_object_security_url_block_list.test.id +} +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigMinimum + +// End of section. //template:end testAccConfigMinimum + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigAll +func testAccSdwanPolicyObjectUnifiedAdvancedInspectionProfileProfileParcelConfig_all() string { + config := `resource "sdwan_policy_object_unified_advanced_inspection_profile" "test" {` + "\n" + config += ` name = "TF_TEST_ALL"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` tls_decryption_action = "decrypt"` + "\n" + config += ` intrusion_prevention_list_id = sdwan_policy_object_unified_intrusion_prevention.test.id` + "\n" + config += ` url_filtering_list_id = sdwan_policy_object_security_url_allow_list.test.id` + "\n" + config += ` advanced_malware_protection_list_id = sdwan_policy_object_unified_advanced_malware_protection.test.id` + "\n" + config += ` tls_ssl_profile_list_id = sdwan_policy_object_unified_tls_ssl_profile.test.id` + "\n" + config += `}` + "\n" + return config +} + +// End of section. //template:end testAccConfigAll diff --git a/templates/guides/changelog.md.tmpl b/templates/guides/changelog.md.tmpl index 27544a70..e037a473 100644 --- a/templates/guides/changelog.md.tmpl +++ b/templates/guides/changelog.md.tmpl @@ -38,6 +38,7 @@ description: |- - Add `sdwan_policy_object_unified_url_filtering` resource and data source - Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source - Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source +- Add `sdwan_policy_object_unified_advanced_inspection_profile` resource and data source ## 0.4.1 From 0ba25176b780ff0c4c3e5240daca25fc6bc57176 Mon Sep 17 00:00:00 2001 From: Sean Conroy Date: Fri, 13 Sep 2024 20:55:15 +0100 Subject: [PATCH 07/11] Add policy object unified tls ssl decryption resource and data source --- CHANGELOG.md | 1 + ...olicy_object_unified_tls_ssl_decryption.md | 49 ++ docs/guides/changelog.md | 1 + ...olicy_object_unified_tls_ssl_decryption.md | 78 +++ .../data-source.tf | 4 + .../import.sh | 1 + .../resource.tf | 18 + ...icy_object_unified_tls_ssl_decryption.yaml | 64 +++ ...cy_object_unified_tls_ssl_decryption.json} | 0 ...olicy_object_unified_tls_ssl_decryption.go | 181 +++++++ ..._object_unified_tls_ssl_decryption_test.go | 103 ++++ ...olicy_object_unified_tls_ssl_decryption.go | 497 ++++++++++++++++++ internal/provider/provider.go | 2 + ...olicy_object_unified_tls_ssl_decryption.go | 332 ++++++++++++ ..._object_unified_tls_ssl_decryption_test.go | 101 ++++ templates/guides/changelog.md.tmpl | 1 + 16 files changed, 1433 insertions(+) create mode 100644 docs/data-sources/policy_object_unified_tls_ssl_decryption.md create mode 100644 docs/resources/policy_object_unified_tls_ssl_decryption.md create mode 100644 examples/data-sources/sdwan_policy_object_unified_tls_ssl_decryption/data-source.tf create mode 100644 examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/import.sh create mode 100644 examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf create mode 100644 gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml rename gen/models/profile_parcels/{policy_object_unified_ssl_decryption.json => policy_object_unified_tls_ssl_decryption.json} (100%) create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption.go create mode 100644 internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go create mode 100644 internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption.go create mode 100644 internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go diff --git a/CHANGELOG.md b/CHANGELOG.md index 903bacd2..9879bbbc 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -30,6 +30,7 @@ - Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source - Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source - Add `sdwan_policy_object_unified_advanced_inspection_profile` resource and data source +- Add `sdwan_policy_object_unified_tls_ssl_decryption` resource and data source ## 0.4.1 diff --git a/docs/data-sources/policy_object_unified_tls_ssl_decryption.md b/docs/data-sources/policy_object_unified_tls_ssl_decryption.md new file mode 100644 index 00000000..3f535ee7 --- /dev/null +++ b/docs/data-sources/policy_object_unified_tls_ssl_decryption.md @@ -0,0 +1,49 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_tls_ssl_decryption Data Source - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This data source can read the Policy Object Unified TLS SSL Decryption Policy_object. +--- + +# sdwan_policy_object_unified_tls_ssl_decryption (Data Source) + +This data source can read the Policy Object Unified TLS SSL Decryption Policy_object. + +## Example Usage + +```terraform +data "sdwan_policy_object_unified_tls_ssl_decryption" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} +``` + + +## Schema + +### Required + +- `feature_profile_id` (String) Feature Profile ID +- `id` (String) The id of the Policy_object + +### Read-Only + +- `bundle_string` (String) +- `certificate_lifetime` (String) If you have vManage as CA or vManage as intermediate CA, this value should be 1 +- `certificate_revocation_status` (String) If value is none unknown status not required, if value is ocsp then unknown status is required +- `default_ca_certificate_bundle` (Boolean) +- `description` (String) The description of the Policy_object +- `ec_key_type` (String) +- `enable_ssl` (Boolean) If false, no other fields should be provided, if true all fields should be provided +- `expired_certificate` (String) +- `failure_mode` (String) +- `file_name` (String) +- `minimal_tls_ver` (String) +- `name` (String) The name of the Policy_object +- `rsa_keypair_modules` (String) +- `unknown_revocation_status` (String) Only required if certificateRevocationStatus is oscp, if value is none then field shouldn't be here +- `unsupported_cipher_suites` (String) +- `unsupported_protocol_versions` (String) +- `untrusted_certificate` (String) +- `version` (Number) The version of the Policy_object diff --git a/docs/guides/changelog.md b/docs/guides/changelog.md index e037a473..452efa62 100644 --- a/docs/guides/changelog.md +++ b/docs/guides/changelog.md @@ -39,6 +39,7 @@ description: |- - Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source - Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source - Add `sdwan_policy_object_unified_advanced_inspection_profile` resource and data source +- Add `sdwan_policy_object_unified_tls_ssl_decryption` resource and data source ## 0.4.1 diff --git a/docs/resources/policy_object_unified_tls_ssl_decryption.md b/docs/resources/policy_object_unified_tls_ssl_decryption.md new file mode 100644 index 00000000..e298d7e4 --- /dev/null +++ b/docs/resources/policy_object_unified_tls_ssl_decryption.md @@ -0,0 +1,78 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_unified_tls_ssl_decryption Resource - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This resource can manage a Policy Object Unified TLS SSL Decryption Policy_object. + Minimum SD-WAN Manager version: 20.12.0 +--- + +# sdwan_policy_object_unified_tls_ssl_decryption (Resource) + +This resource can manage a Policy Object Unified TLS SSL Decryption Policy_object. + - Minimum SD-WAN Manager version: `20.12.0` + +## Example Usage + +```terraform +resource "sdwan_policy_object_unified_tls_ssl_decryption" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + enable_ssl = true + expired_certificate = "drop" + untrusted_certificate = "drop" + certificate_revocation_status = "ocsp" + unknown_revocation_status = "decrypt" + unsupported_protocol_versions = "no-decrypt" + unsupported_cipher_suites = "drop" + failure_mode = "close" + default_ca_certificate_bundle = true + rsa_keypair_modules = "2048" + ec_key_type = "P384" + certificate_lifetime = "1" + minimal_tls_ver = "TLSv1.2" +} +``` + + +## Schema + +### Required + +- `certificate_lifetime` (String) If you have vManage as CA or vManage as intermediate CA, this value should be 1 +- `certificate_revocation_status` (String) If value is none unknown status not required, if value is ocsp then unknown status is required + - Choices: `ocsp`, `none` +- `ec_key_type` (String) - Choices: `P256`, `P384`, `P521` +- `enable_ssl` (Boolean) If false, no other fields should be provided, if true all fields should be provided +- `expired_certificate` (String) - Choices: `decrypt`, `drop` +- `failure_mode` (String) - Choices: `close`, `open` +- `feature_profile_id` (String) Feature Profile ID +- `minimal_tls_ver` (String) - Choices: `TLSv1`, `TLSv1.1`, `TLSv1.2` +- `name` (String) The name of the Policy_object +- `rsa_keypair_modules` (String) - Choices: `1024`, `2048`, `4096` +- `unknown_revocation_status` (String) Only required if certificateRevocationStatus is oscp, if value is none then field shouldn't be here + - Choices: `decrypt`, `drop` +- `unsupported_cipher_suites` (String) - Choices: `no-decrypt`, `drop` +- `unsupported_protocol_versions` (String) - Choices: `no-decrypt`, `drop` +- `untrusted_certificate` (String) - Choices: `decrypt`, `drop` + +### Optional + +- `bundle_string` (String) +- `default_ca_certificate_bundle` (Boolean) +- `description` (String) The description of the Policy_object +- `file_name` (String) + +### Read-Only + +- `id` (String) The id of the Policy_object +- `version` (Number) The version of the Policy_object + +## Import + +Import is supported using the following syntax: + +```shell +terraform import sdwan_policy_object_unified_tls_ssl_decryption.example "f6b2c44c-693c-4763-b010-895aa3d236bd" +``` diff --git a/examples/data-sources/sdwan_policy_object_unified_tls_ssl_decryption/data-source.tf b/examples/data-sources/sdwan_policy_object_unified_tls_ssl_decryption/data-source.tf new file mode 100644 index 00000000..230fe070 --- /dev/null +++ b/examples/data-sources/sdwan_policy_object_unified_tls_ssl_decryption/data-source.tf @@ -0,0 +1,4 @@ +data "sdwan_policy_object_unified_tls_ssl_decryption" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} diff --git a/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/import.sh b/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/import.sh new file mode 100644 index 00000000..ee277da6 --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/import.sh @@ -0,0 +1 @@ +terraform import sdwan_policy_object_unified_tls_ssl_decryption.example "f6b2c44c-693c-4763-b010-895aa3d236bd" diff --git a/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf b/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf new file mode 100644 index 00000000..23a90771 --- /dev/null +++ b/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf @@ -0,0 +1,18 @@ +resource "sdwan_policy_object_unified_tls_ssl_decryption" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + enable_ssl = true + expired_certificate = "drop" + untrusted_certificate = "drop" + certificate_revocation_status = "ocsp" + unknown_revocation_status = "decrypt" + unsupported_protocol_versions = "no-decrypt" + unsupported_cipher_suites = "drop" + failure_mode = "close" + default_ca_certificate_bundle = true + rsa_keypair_modules = "2048" + ec_key_type = "P384" + certificate_lifetime = "1" + minimal_tls_ver = "TLSv1.2" +} diff --git a/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml b/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml new file mode 100644 index 00000000..bbe1e470 --- /dev/null +++ b/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml @@ -0,0 +1,64 @@ +--- +name: Policy Object Unified TLS SSL Decryption +rest_endpoint: /v1/feature-profile/sdwan/policy-object/%v/unified/unified/ssl-decryption +minimum_version: 20.12.0 +test_tags: [SDWAN_2012] +skip_minimum_test: true +parcel_type: policy_object +attributes: + - tf_name: feature_profile_id + reference: true + type: String + mandatory: true + description: Feature Profile ID + example: f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac + test_value: sdwan_policy_object_feature_profile.test.id + - model_name: sslEnable + tf_name: enable_ssl + example: true + - model_name: expiredCertificate + example: drop + - model_name: untrustedCertificate + example: drop + - model_name: certificateRevocationStatus + example: ocsp + - model_name: unknownStatus + tf_name: unknown_revocation_status + example: decrypt + - model_name: unsupportedProtocolVersions + example: no-decrypt + - model_name: unsupportedCipherSuites + example: drop + - model_name: failureMode + example: close + - model_name: default + tf_name: default_ca_certificate_bundle + data_path: [caCertBundle] + example: true + - model_name: fileName + data_path: [caCertBundle] + exclude_test: true + example: dummy.pem + - model_name: bundleString + data_path: [caCertBundle] + exclude_test: true + example: testString + - model_name: keyModulus + tf_name: rsa_keypair_modules + example: 2048 + - model_name: eckeyType + tf_name: ec_key_type + example: P384 + - model_name: certificateLifetime + example: 1 + - model_name: minTlsVer + tf_name: minimal_tls_ver + example: TLSv1.2 + - model_name: caTpLabel + value: PROXY-SIGNING-CA + +test_prerequisites: | + resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" + } \ No newline at end of file diff --git a/gen/models/profile_parcels/policy_object_unified_ssl_decryption.json b/gen/models/profile_parcels/policy_object_unified_tls_ssl_decryption.json similarity index 100% rename from gen/models/profile_parcels/policy_object_unified_ssl_decryption.json rename to gen/models/profile_parcels/policy_object_unified_tls_ssl_decryption.json diff --git a/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption.go b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption.go new file mode 100644 index 00000000..9832cb63 --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption.go @@ -0,0 +1,181 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/hashicorp/terraform-plugin-framework/datasource" + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure the implementation satisfies the expected interfaces. +var ( + _ datasource.DataSource = &PolicyObjectUnifiedTLSSSLDecryptionProfileParcelDataSource{} + _ datasource.DataSourceWithConfigure = &PolicyObjectUnifiedTLSSSLDecryptionProfileParcelDataSource{} +) + +func NewPolicyObjectUnifiedTLSSSLDecryptionProfileParcelDataSource() datasource.DataSource { + return &PolicyObjectUnifiedTLSSSLDecryptionProfileParcelDataSource{} +} + +type PolicyObjectUnifiedTLSSSLDecryptionProfileParcelDataSource struct { + client *sdwan.Client +} + +func (d *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelDataSource) Metadata(_ context.Context, req datasource.MetadataRequest, resp *datasource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_tls_ssl_decryption" +} + +func (d *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelDataSource) Schema(ctx context.Context, req datasource.SchemaRequest, resp *datasource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: "This data source can read the Policy Object Unified TLS SSL Decryption Policy_object.", + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Required: true, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Computed: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Computed: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: "Feature Profile ID", + Required: true, + }, + "enable_ssl": schema.BoolAttribute{ + MarkdownDescription: "If false, no other fields should be provided, if true all fields should be provided", + Computed: true, + }, + "expired_certificate": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "untrusted_certificate": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "certificate_revocation_status": schema.StringAttribute{ + MarkdownDescription: "If value is none unknown status not required, if value is ocsp then unknown status is required", + Computed: true, + }, + "unknown_revocation_status": schema.StringAttribute{ + MarkdownDescription: "Only required if certificateRevocationStatus is oscp, if value is none then field shouldn't be here", + Computed: true, + }, + "unsupported_protocol_versions": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "unsupported_cipher_suites": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "failure_mode": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "default_ca_certificate_bundle": schema.BoolAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "file_name": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "bundle_string": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "rsa_keypair_modules": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "ec_key_type": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + "certificate_lifetime": schema.StringAttribute{ + MarkdownDescription: "If you have vManage as CA or vManage as intermediate CA, this value should be 1", + Computed: true, + }, + "minimal_tls_ver": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + }, + } +} + +func (d *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelDataSource) Configure(_ context.Context, req datasource.ConfigureRequest, _ *datasource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + d.client = req.ProviderData.(*SdwanProviderData).Client +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (d *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelDataSource) Read(ctx context.Context, req datasource.ReadRequest, resp *datasource.ReadResponse) { + var config PolicyObjectUnifiedTLSSSLDecryption + + // Read config + diags := req.Config.Get(ctx, &config) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", config.Id.String())) + + res, err := d.client.Get(config.getPath() + "/" + url.QueryEscape(config.Id.ValueString())) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object, got error: %s", err)) + return + } + + config.fromBody(ctx, res) + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", config.Name.ValueString())) + + diags = resp.State.Set(ctx, &config) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read diff --git a/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go new file mode 100644 index 00000000..a42c26d9 --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go @@ -0,0 +1,103 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSource +func TestAccDataSourceSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "enable_ssl", "true")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "expired_certificate", "drop")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "untrusted_certificate", "drop")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "certificate_revocation_status", "ocsp")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "unknown_revocation_status", "decrypt")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_protocol_versions", "no-decrypt")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_cipher_suites", "drop")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "failure_mode", "close")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "default_ca_certificate_bundle", "true")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "rsa_keypair_modules", "2048")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "ec_key_type", "P384")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "certificate_lifetime", "1")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "minimal_tls_ver", "TLSv1.2")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + { + Config: testAccDataSourceSdwanPolicyObjectUnifiedTLSSSLDecryptionPrerequisitesProfileParcelConfig + testAccDataSourceSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcelConfig(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAccDataSource + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccDataSourceSdwanPolicyObjectUnifiedTLSSSLDecryptionPrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSourceConfig +func testAccDataSourceSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcelConfig() string { + config := `resource "sdwan_policy_object_unified_tls_ssl_decryption" "test" {` + "\n" + config += ` name = "TF_TEST"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` enable_ssl = true` + "\n" + config += ` expired_certificate = "drop"` + "\n" + config += ` untrusted_certificate = "drop"` + "\n" + config += ` certificate_revocation_status = "ocsp"` + "\n" + config += ` unknown_revocation_status = "decrypt"` + "\n" + config += ` unsupported_protocol_versions = "no-decrypt"` + "\n" + config += ` unsupported_cipher_suites = "drop"` + "\n" + config += ` failure_mode = "close"` + "\n" + config += ` default_ca_certificate_bundle = true` + "\n" + config += ` rsa_keypair_modules = "2048"` + "\n" + config += ` ec_key_type = "P384"` + "\n" + config += ` certificate_lifetime = "1"` + "\n" + config += ` minimal_tls_ver = "TLSv1.2"` + "\n" + config += `}` + "\n" + + config += ` + data "sdwan_policy_object_unified_tls_ssl_decryption" "test" { + id = sdwan_policy_object_unified_tls_ssl_decryption.test.id + feature_profile_id = sdwan_policy_object_feature_profile.test.id + } + ` + return config +} + +// End of section. //template:end testAccDataSourceConfig diff --git a/internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go b/internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go new file mode 100644 index 00000000..c717b675 --- /dev/null +++ b/internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go @@ -0,0 +1,497 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/tidwall/gjson" + "github.com/tidwall/sjson" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin types +type PolicyObjectUnifiedTLSSSLDecryption struct { + Id types.String `tfsdk:"id"` + Version types.Int64 `tfsdk:"version"` + Name types.String `tfsdk:"name"` + Description types.String `tfsdk:"description"` + FeatureProfileId types.String `tfsdk:"feature_profile_id"` + EnableSsl types.Bool `tfsdk:"enable_ssl"` + ExpiredCertificate types.String `tfsdk:"expired_certificate"` + UntrustedCertificate types.String `tfsdk:"untrusted_certificate"` + CertificateRevocationStatus types.String `tfsdk:"certificate_revocation_status"` + UnknownRevocationStatus types.String `tfsdk:"unknown_revocation_status"` + UnsupportedProtocolVersions types.String `tfsdk:"unsupported_protocol_versions"` + UnsupportedCipherSuites types.String `tfsdk:"unsupported_cipher_suites"` + FailureMode types.String `tfsdk:"failure_mode"` + DefaultCaCertificateBundle types.Bool `tfsdk:"default_ca_certificate_bundle"` + FileName types.String `tfsdk:"file_name"` + BundleString types.String `tfsdk:"bundle_string"` + RsaKeypairModules types.String `tfsdk:"rsa_keypair_modules"` + EcKeyType types.String `tfsdk:"ec_key_type"` + CertificateLifetime types.String `tfsdk:"certificate_lifetime"` + MinimalTlsVer types.String `tfsdk:"minimal_tls_ver"` +} + +// End of section. //template:end types + +// Section below is generated&owned by "gen/generator.go". //template:begin getModel +func (data PolicyObjectUnifiedTLSSSLDecryption) getModel() string { + return "policy_object_unified_tls_ssl_decryption" +} + +// End of section. //template:end getModel + +// Section below is generated&owned by "gen/generator.go". //template:begin getPath +func (data PolicyObjectUnifiedTLSSSLDecryption) getPath() string { + return fmt.Sprintf("/v1/feature-profile/sdwan/policy-object/%v/unified/unified/ssl-decryption", url.QueryEscape(data.FeatureProfileId.ValueString())) +} + +// End of section. //template:end getPath + +// Section below is generated&owned by "gen/generator.go". //template:begin toBody +func (data PolicyObjectUnifiedTLSSSLDecryption) toBody(ctx context.Context) string { + body := "" + body, _ = sjson.Set(body, "name", data.Name.ValueString()) + body, _ = sjson.Set(body, "description", data.Description.ValueString()) + path := "data." + if !data.EnableSsl.IsNull() { + if true { + body, _ = sjson.Set(body, path+"sslEnable.optionType", "global") + body, _ = sjson.Set(body, path+"sslEnable.value", data.EnableSsl.ValueBool()) + } + } + if !data.ExpiredCertificate.IsNull() { + if true { + body, _ = sjson.Set(body, path+"expiredCertificate.optionType", "global") + body, _ = sjson.Set(body, path+"expiredCertificate.value", data.ExpiredCertificate.ValueString()) + } + } + if !data.UntrustedCertificate.IsNull() { + if true { + body, _ = sjson.Set(body, path+"untrustedCertificate.optionType", "global") + body, _ = sjson.Set(body, path+"untrustedCertificate.value", data.UntrustedCertificate.ValueString()) + } + } + if !data.CertificateRevocationStatus.IsNull() { + if true { + body, _ = sjson.Set(body, path+"certificateRevocationStatus.optionType", "global") + body, _ = sjson.Set(body, path+"certificateRevocationStatus.value", data.CertificateRevocationStatus.ValueString()) + } + } + if !data.UnknownRevocationStatus.IsNull() { + if true { + body, _ = sjson.Set(body, path+"unknownStatus.optionType", "global") + body, _ = sjson.Set(body, path+"unknownStatus.value", data.UnknownRevocationStatus.ValueString()) + } + } + if !data.UnsupportedProtocolVersions.IsNull() { + if true { + body, _ = sjson.Set(body, path+"unsupportedProtocolVersions.optionType", "global") + body, _ = sjson.Set(body, path+"unsupportedProtocolVersions.value", data.UnsupportedProtocolVersions.ValueString()) + } + } + if !data.UnsupportedCipherSuites.IsNull() { + if true { + body, _ = sjson.Set(body, path+"unsupportedCipherSuites.optionType", "global") + body, _ = sjson.Set(body, path+"unsupportedCipherSuites.value", data.UnsupportedCipherSuites.ValueString()) + } + } + if !data.FailureMode.IsNull() { + if true { + body, _ = sjson.Set(body, path+"failureMode.optionType", "global") + body, _ = sjson.Set(body, path+"failureMode.value", data.FailureMode.ValueString()) + } + } + if !data.DefaultCaCertificateBundle.IsNull() { + if true { + body, _ = sjson.Set(body, path+"caCertBundle.default.optionType", "global") + body, _ = sjson.Set(body, path+"caCertBundle.default.value", data.DefaultCaCertificateBundle.ValueBool()) + } + } + if !data.FileName.IsNull() { + if true { + body, _ = sjson.Set(body, path+"caCertBundle.fileName.optionType", "global") + body, _ = sjson.Set(body, path+"caCertBundle.fileName.value", data.FileName.ValueString()) + } + } + if !data.BundleString.IsNull() { + if true { + body, _ = sjson.Set(body, path+"caCertBundle.bundleString.optionType", "global") + body, _ = sjson.Set(body, path+"caCertBundle.bundleString.value", data.BundleString.ValueString()) + } + } + if !data.RsaKeypairModules.IsNull() { + if true { + body, _ = sjson.Set(body, path+"keyModulus.optionType", "global") + body, _ = sjson.Set(body, path+"keyModulus.value", data.RsaKeypairModules.ValueString()) + } + } + if !data.EcKeyType.IsNull() { + if true { + body, _ = sjson.Set(body, path+"eckeyType.optionType", "global") + body, _ = sjson.Set(body, path+"eckeyType.value", data.EcKeyType.ValueString()) + } + } + if !data.CertificateLifetime.IsNull() { + if true { + body, _ = sjson.Set(body, path+"certificateLifetime.optionType", "global") + body, _ = sjson.Set(body, path+"certificateLifetime.value", data.CertificateLifetime.ValueString()) + } + } + if !data.MinimalTlsVer.IsNull() { + if true { + body, _ = sjson.Set(body, path+"minTlsVer.optionType", "global") + body, _ = sjson.Set(body, path+"minTlsVer.value", data.MinimalTlsVer.ValueString()) + } + } + if true { + body, _ = sjson.Set(body, path+"caTpLabel.optionType", "default") + body, _ = sjson.Set(body, path+"caTpLabel.value", "PROXY-SIGNING-CA") + } + return body +} + +// End of section. //template:end toBody + +// Section below is generated&owned by "gen/generator.go". //template:begin fromBody +func (data *PolicyObjectUnifiedTLSSSLDecryption) fromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.EnableSsl = types.BoolNull() + + if t := res.Get(path + "sslEnable.optionType"); t.Exists() { + va := res.Get(path + "sslEnable.value") + if t.String() == "global" { + data.EnableSsl = types.BoolValue(va.Bool()) + } + } + data.ExpiredCertificate = types.StringNull() + + if t := res.Get(path + "expiredCertificate.optionType"); t.Exists() { + va := res.Get(path + "expiredCertificate.value") + if t.String() == "global" { + data.ExpiredCertificate = types.StringValue(va.String()) + } + } + data.UntrustedCertificate = types.StringNull() + + if t := res.Get(path + "untrustedCertificate.optionType"); t.Exists() { + va := res.Get(path + "untrustedCertificate.value") + if t.String() == "global" { + data.UntrustedCertificate = types.StringValue(va.String()) + } + } + data.CertificateRevocationStatus = types.StringNull() + + if t := res.Get(path + "certificateRevocationStatus.optionType"); t.Exists() { + va := res.Get(path + "certificateRevocationStatus.value") + if t.String() == "global" { + data.CertificateRevocationStatus = types.StringValue(va.String()) + } + } + data.UnknownRevocationStatus = types.StringNull() + + if t := res.Get(path + "unknownStatus.optionType"); t.Exists() { + va := res.Get(path + "unknownStatus.value") + if t.String() == "global" { + data.UnknownRevocationStatus = types.StringValue(va.String()) + } + } + data.UnsupportedProtocolVersions = types.StringNull() + + if t := res.Get(path + "unsupportedProtocolVersions.optionType"); t.Exists() { + va := res.Get(path + "unsupportedProtocolVersions.value") + if t.String() == "global" { + data.UnsupportedProtocolVersions = types.StringValue(va.String()) + } + } + data.UnsupportedCipherSuites = types.StringNull() + + if t := res.Get(path + "unsupportedCipherSuites.optionType"); t.Exists() { + va := res.Get(path + "unsupportedCipherSuites.value") + if t.String() == "global" { + data.UnsupportedCipherSuites = types.StringValue(va.String()) + } + } + data.FailureMode = types.StringNull() + + if t := res.Get(path + "failureMode.optionType"); t.Exists() { + va := res.Get(path + "failureMode.value") + if t.String() == "global" { + data.FailureMode = types.StringValue(va.String()) + } + } + data.DefaultCaCertificateBundle = types.BoolNull() + + if t := res.Get(path + "caCertBundle.default.optionType"); t.Exists() { + va := res.Get(path + "caCertBundle.default.value") + if t.String() == "global" { + data.DefaultCaCertificateBundle = types.BoolValue(va.Bool()) + } + } + data.FileName = types.StringNull() + + if t := res.Get(path + "caCertBundle.fileName.optionType"); t.Exists() { + va := res.Get(path + "caCertBundle.fileName.value") + if t.String() == "global" { + data.FileName = types.StringValue(va.String()) + } + } + data.BundleString = types.StringNull() + + if t := res.Get(path + "caCertBundle.bundleString.optionType"); t.Exists() { + va := res.Get(path + "caCertBundle.bundleString.value") + if t.String() == "global" { + data.BundleString = types.StringValue(va.String()) + } + } + data.RsaKeypairModules = types.StringNull() + + if t := res.Get(path + "keyModulus.optionType"); t.Exists() { + va := res.Get(path + "keyModulus.value") + if t.String() == "global" { + data.RsaKeypairModules = types.StringValue(va.String()) + } + } + data.EcKeyType = types.StringNull() + + if t := res.Get(path + "eckeyType.optionType"); t.Exists() { + va := res.Get(path + "eckeyType.value") + if t.String() == "global" { + data.EcKeyType = types.StringValue(va.String()) + } + } + data.CertificateLifetime = types.StringNull() + + if t := res.Get(path + "certificateLifetime.optionType"); t.Exists() { + va := res.Get(path + "certificateLifetime.value") + if t.String() == "global" { + data.CertificateLifetime = types.StringValue(va.String()) + } + } + data.MinimalTlsVer = types.StringNull() + + if t := res.Get(path + "minTlsVer.optionType"); t.Exists() { + va := res.Get(path + "minTlsVer.value") + if t.String() == "global" { + data.MinimalTlsVer = types.StringValue(va.String()) + } + } +} + +// End of section. //template:end fromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin updateFromBody +func (data *PolicyObjectUnifiedTLSSSLDecryption) updateFromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + data.EnableSsl = types.BoolNull() + + if t := res.Get(path + "sslEnable.optionType"); t.Exists() { + va := res.Get(path + "sslEnable.value") + if t.String() == "global" { + data.EnableSsl = types.BoolValue(va.Bool()) + } + } + data.ExpiredCertificate = types.StringNull() + + if t := res.Get(path + "expiredCertificate.optionType"); t.Exists() { + va := res.Get(path + "expiredCertificate.value") + if t.String() == "global" { + data.ExpiredCertificate = types.StringValue(va.String()) + } + } + data.UntrustedCertificate = types.StringNull() + + if t := res.Get(path + "untrustedCertificate.optionType"); t.Exists() { + va := res.Get(path + "untrustedCertificate.value") + if t.String() == "global" { + data.UntrustedCertificate = types.StringValue(va.String()) + } + } + data.CertificateRevocationStatus = types.StringNull() + + if t := res.Get(path + "certificateRevocationStatus.optionType"); t.Exists() { + va := res.Get(path + "certificateRevocationStatus.value") + if t.String() == "global" { + data.CertificateRevocationStatus = types.StringValue(va.String()) + } + } + data.UnknownRevocationStatus = types.StringNull() + + if t := res.Get(path + "unknownStatus.optionType"); t.Exists() { + va := res.Get(path + "unknownStatus.value") + if t.String() == "global" { + data.UnknownRevocationStatus = types.StringValue(va.String()) + } + } + data.UnsupportedProtocolVersions = types.StringNull() + + if t := res.Get(path + "unsupportedProtocolVersions.optionType"); t.Exists() { + va := res.Get(path + "unsupportedProtocolVersions.value") + if t.String() == "global" { + data.UnsupportedProtocolVersions = types.StringValue(va.String()) + } + } + data.UnsupportedCipherSuites = types.StringNull() + + if t := res.Get(path + "unsupportedCipherSuites.optionType"); t.Exists() { + va := res.Get(path + "unsupportedCipherSuites.value") + if t.String() == "global" { + data.UnsupportedCipherSuites = types.StringValue(va.String()) + } + } + data.FailureMode = types.StringNull() + + if t := res.Get(path + "failureMode.optionType"); t.Exists() { + va := res.Get(path + "failureMode.value") + if t.String() == "global" { + data.FailureMode = types.StringValue(va.String()) + } + } + data.DefaultCaCertificateBundle = types.BoolNull() + + if t := res.Get(path + "caCertBundle.default.optionType"); t.Exists() { + va := res.Get(path + "caCertBundle.default.value") + if t.String() == "global" { + data.DefaultCaCertificateBundle = types.BoolValue(va.Bool()) + } + } + data.FileName = types.StringNull() + + if t := res.Get(path + "caCertBundle.fileName.optionType"); t.Exists() { + va := res.Get(path + "caCertBundle.fileName.value") + if t.String() == "global" { + data.FileName = types.StringValue(va.String()) + } + } + data.BundleString = types.StringNull() + + if t := res.Get(path + "caCertBundle.bundleString.optionType"); t.Exists() { + va := res.Get(path + "caCertBundle.bundleString.value") + if t.String() == "global" { + data.BundleString = types.StringValue(va.String()) + } + } + data.RsaKeypairModules = types.StringNull() + + if t := res.Get(path + "keyModulus.optionType"); t.Exists() { + va := res.Get(path + "keyModulus.value") + if t.String() == "global" { + data.RsaKeypairModules = types.StringValue(va.String()) + } + } + data.EcKeyType = types.StringNull() + + if t := res.Get(path + "eckeyType.optionType"); t.Exists() { + va := res.Get(path + "eckeyType.value") + if t.String() == "global" { + data.EcKeyType = types.StringValue(va.String()) + } + } + data.CertificateLifetime = types.StringNull() + + if t := res.Get(path + "certificateLifetime.optionType"); t.Exists() { + va := res.Get(path + "certificateLifetime.value") + if t.String() == "global" { + data.CertificateLifetime = types.StringValue(va.String()) + } + } + data.MinimalTlsVer = types.StringNull() + + if t := res.Get(path + "minTlsVer.optionType"); t.Exists() { + va := res.Get(path + "minTlsVer.value") + if t.String() == "global" { + data.MinimalTlsVer = types.StringValue(va.String()) + } + } +} + +// End of section. //template:end updateFromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin isNull +func (data *PolicyObjectUnifiedTLSSSLDecryption) isNull(ctx context.Context, res gjson.Result) bool { + if !data.FeatureProfileId.IsNull() { + return false + } + if !data.EnableSsl.IsNull() { + return false + } + if !data.ExpiredCertificate.IsNull() { + return false + } + if !data.UntrustedCertificate.IsNull() { + return false + } + if !data.CertificateRevocationStatus.IsNull() { + return false + } + if !data.UnknownRevocationStatus.IsNull() { + return false + } + if !data.UnsupportedProtocolVersions.IsNull() { + return false + } + if !data.UnsupportedCipherSuites.IsNull() { + return false + } + if !data.FailureMode.IsNull() { + return false + } + if !data.DefaultCaCertificateBundle.IsNull() { + return false + } + if !data.FileName.IsNull() { + return false + } + if !data.BundleString.IsNull() { + return false + } + if !data.RsaKeypairModules.IsNull() { + return false + } + if !data.EcKeyType.IsNull() { + return false + } + if !data.CertificateLifetime.IsNull() { + return false + } + if !data.MinimalTlsVer.IsNull() { + return false + } + return true +} + +// End of section. //template:end isNull diff --git a/internal/provider/provider.go b/internal/provider/provider.go index ef9ff171..a7d11d59 100644 --- a/internal/provider/provider.go +++ b/internal/provider/provider.go @@ -316,6 +316,7 @@ func (p *SdwanProvider) Resources(ctx context.Context) []func() resource.Resourc NewPolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource, NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource, NewPolicyObjectUnifiedIntrusionPreventionProfileParcelResource, + NewPolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource, NewPolicyObjectUnifiedTLSSSLProfileProfileParcelResource, NewPolicyObjectUnifiedURLFilteringProfileParcelResource, NewPolicyObjectVPNGroupProfileParcelResource, @@ -525,6 +526,7 @@ func (p *SdwanProvider) DataSources(ctx context.Context) []func() datasource.Dat NewPolicyObjectUnifiedAdvancedInspectionProfileProfileParcelDataSource, NewPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource, NewPolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource, + NewPolicyObjectUnifiedTLSSSLDecryptionProfileParcelDataSource, NewPolicyObjectUnifiedTLSSSLProfileProfileParcelDataSource, NewPolicyObjectUnifiedURLFilteringProfileParcelDataSource, NewPolicyObjectVPNGroupProfileParcelDataSource, diff --git a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption.go b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption.go new file mode 100644 index 00000000..e64113aa --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption.go @@ -0,0 +1,332 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + "sync" + + "github.com/CiscoDevNet/terraform-provider-sdwan/internal/provider/helpers" + "github.com/hashicorp/terraform-plugin-framework-validators/stringvalidator" + "github.com/hashicorp/terraform-plugin-framework/path" + "github.com/hashicorp/terraform-plugin-framework/resource" + "github.com/hashicorp/terraform-plugin-framework/resource/schema" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/planmodifier" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/stringplanmodifier" + "github.com/hashicorp/terraform-plugin-framework/schema/validator" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure provider defined types fully satisfy framework interfaces +var _ resource.Resource = &PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource{} +var _ resource.ResourceWithImportState = &PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource{} + +func NewPolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource() resource.Resource { + return &PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource{} +} + +type PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource struct { + client *sdwan.Client + updateMutex *sync.Mutex +} + +func (r *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource) Metadata(ctx context.Context, req resource.MetadataRequest, resp *resource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_unified_tls_ssl_decryption" +} + +func (r *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource) Schema(ctx context.Context, req resource.SchemaRequest, resp *resource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: helpers.NewAttributeDescription("This resource can manage a Policy Object Unified TLS SSL Decryption Policy_object.").AddMinimumVersionDescription("20.12.0").String, + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Computed: true, + PlanModifiers: []planmodifier.String{ + stringplanmodifier.UseStateForUnknown(), + }, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Required: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Optional: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Feature Profile ID").String, + Required: true, + }, + "enable_ssl": schema.BoolAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("If false, no other fields should be provided, if true all fields should be provided").String, + Required: true, + }, + "expired_certificate": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("decrypt", "drop").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("decrypt", "drop"), + }, + }, + "untrusted_certificate": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("decrypt", "drop").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("decrypt", "drop"), + }, + }, + "certificate_revocation_status": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("If value is none unknown status not required, if value is ocsp then unknown status is required").AddStringEnumDescription("ocsp", "none").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("ocsp", "none"), + }, + }, + "unknown_revocation_status": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Only required if certificateRevocationStatus is oscp, if value is none then field shouldn't be here").AddStringEnumDescription("decrypt", "drop").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("decrypt", "drop"), + }, + }, + "unsupported_protocol_versions": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("no-decrypt", "drop").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("no-decrypt", "drop"), + }, + }, + "unsupported_cipher_suites": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("no-decrypt", "drop").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("no-decrypt", "drop"), + }, + }, + "failure_mode": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("close", "open").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("close", "open"), + }, + }, + "default_ca_certificate_bundle": schema.BoolAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Optional: true, + }, + "file_name": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Optional: true, + }, + "bundle_string": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Optional: true, + }, + "rsa_keypair_modules": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("1024", "2048", "4096").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("1024", "2048", "4096"), + }, + }, + "ec_key_type": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("P256", "P384", "P521").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("P256", "P384", "P521"), + }, + }, + "certificate_lifetime": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("If you have vManage as CA or vManage as intermediate CA, this value should be 1").String, + Required: true, + }, + "minimal_tls_ver": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("TLSv1", "TLSv1.1", "TLSv1.2").String, + Required: true, + Validators: []validator.String{ + stringvalidator.OneOf("TLSv1", "TLSv1.1", "TLSv1.2"), + }, + }, + }, + } +} + +func (r *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource) Configure(_ context.Context, req resource.ConfigureRequest, _ *resource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + r.client = req.ProviderData.(*SdwanProviderData).Client + r.updateMutex = req.ProviderData.(*SdwanProviderData).UpdateMutex +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin create +func (r *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource) Create(ctx context.Context, req resource.CreateRequest, resp *resource.CreateResponse) { + var plan PolicyObjectUnifiedTLSSSLDecryption + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Create", plan.Name.ValueString())) + + // Create object + body := plan.toBody(ctx) + + res, err := r.client.Post(plan.getPath(), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (POST), got error: %s, %s", err, res.String())) + return + } + + plan.Id = types.StringValue(res.Get("parcelId").String()) + plan.Version = types.Int64Value(0) + + tflog.Debug(ctx, fmt.Sprintf("%s: Create finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end create + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (r *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource) Read(ctx context.Context, req resource.ReadRequest, resp *resource.ReadResponse) { + var state PolicyObjectUnifiedTLSSSLDecryption + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", state.Name.String())) + + res, err := r.client.Get(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if res.Get("error.message").String() == "Invalid feature Id" { + resp.State.RemoveResource(ctx) + return + } else if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object (GET), got error: %s, %s", err, res.String())) + return + } + + // If every attribute is set to null we are dealing with an import operation and therefore reading all attributes + if state.isNull(ctx, res) { + state.fromBody(ctx, res) + } else { + state.updateFromBody(ctx, res) + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", state.Name.ValueString())) + + diags = resp.State.Set(ctx, &state) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read + +// Section below is generated&owned by "gen/generator.go". //template:begin update +func (r *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource) Update(ctx context.Context, req resource.UpdateRequest, resp *resource.UpdateResponse) { + var plan, state PolicyObjectUnifiedTLSSSLDecryption + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + // Read state + diags = req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Update", plan.Name.ValueString())) + + body := plan.toBody(ctx) + res, err := r.client.Put(plan.getPath()+"/"+url.QueryEscape(plan.Id.ValueString()), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (PUT), got error: %s, %s", err, res.String())) + return + } + + plan.Version = types.Int64Value(state.Version.ValueInt64() + 1) + + tflog.Debug(ctx, fmt.Sprintf("%s: Update finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end update + +// Section below is generated&owned by "gen/generator.go". //template:begin delete +func (r *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource) Delete(ctx context.Context, req resource.DeleteRequest, resp *resource.DeleteResponse) { + var state PolicyObjectUnifiedTLSSSLDecryption + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Delete", state.Name.ValueString())) + + res, err := r.client.Delete(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if err != nil && res.Get("error.message").String() != "Invalid Template Id" { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to delete object (DELETE), got error: %s, %s", err, res.String())) + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Delete finished successfully", state.Name.ValueString())) + + resp.State.RemoveResource(ctx) +} + +// End of section. //template:end delete + +// Section below is generated&owned by "gen/generator.go". //template:begin import +func (r *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource) ImportState(ctx context.Context, req resource.ImportStateRequest, resp *resource.ImportStateResponse) { + resource.ImportStatePassthroughID(ctx, path.Root("id"), req, resp) +} + +// End of section. //template:end import diff --git a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go new file mode 100644 index 00000000..3fd3f08b --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go @@ -0,0 +1,101 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAcc +func TestAccSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "enable_ssl", "true")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "expired_certificate", "drop")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "untrusted_certificate", "drop")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "certificate_revocation_status", "ocsp")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "unknown_revocation_status", "decrypt")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_protocol_versions", "no-decrypt")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_cipher_suites", "drop")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "failure_mode", "close")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "default_ca_certificate_bundle", "true")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "rsa_keypair_modules", "2048")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "ec_key_type", "P384")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "certificate_lifetime", "1")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "minimal_tls_ver", "TLSv1.2")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + + { + Config: testAccSdwanPolicyObjectUnifiedTLSSSLDecryptionPrerequisitesProfileParcelConfig + testAccSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcelConfig_all(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAcc + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccSdwanPolicyObjectUnifiedTLSSSLDecryptionPrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigMinimum + +// End of section. //template:end testAccConfigMinimum + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigAll +func testAccSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcelConfig_all() string { + config := `resource "sdwan_policy_object_unified_tls_ssl_decryption" "test" {` + "\n" + config += ` name = "TF_TEST_ALL"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` enable_ssl = true` + "\n" + config += ` expired_certificate = "drop"` + "\n" + config += ` untrusted_certificate = "drop"` + "\n" + config += ` certificate_revocation_status = "ocsp"` + "\n" + config += ` unknown_revocation_status = "decrypt"` + "\n" + config += ` unsupported_protocol_versions = "no-decrypt"` + "\n" + config += ` unsupported_cipher_suites = "drop"` + "\n" + config += ` failure_mode = "close"` + "\n" + config += ` default_ca_certificate_bundle = true` + "\n" + config += ` rsa_keypair_modules = "2048"` + "\n" + config += ` ec_key_type = "P384"` + "\n" + config += ` certificate_lifetime = "1"` + "\n" + config += ` minimal_tls_ver = "TLSv1.2"` + "\n" + config += `}` + "\n" + return config +} + +// End of section. //template:end testAccConfigAll diff --git a/templates/guides/changelog.md.tmpl b/templates/guides/changelog.md.tmpl index e037a473..452efa62 100644 --- a/templates/guides/changelog.md.tmpl +++ b/templates/guides/changelog.md.tmpl @@ -39,6 +39,7 @@ description: |- - Add `sdwan_policy_object_unified_tls_ssl_profile` resource and data source - Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source - Add `sdwan_policy_object_unified_advanced_inspection_profile` resource and data source +- Add `sdwan_policy_object_unified_tls_ssl_decryption` resource and data source ## 0.4.1 From c412a213a0294a22184696588601bf6e21e0f9d6 Mon Sep 17 00:00:00 2001 From: Sean Conroy Date: Fri, 13 Sep 2024 21:33:39 +0100 Subject: [PATCH 08/11] Add policy object security protocol list resource and data source --- CHANGELOG.md | 1 + .../policy_object_security_protocol_list.md | 42 +++ docs/guides/changelog.md | 1 + .../policy_object_security_protocol_list.md | 61 +++++ .../data-source.tf | 4 + .../import.sh | 1 + .../resource.tf | 10 + .../policy_object_security_protocol_list.yaml | 29 ++ ...policy_object_security_protocol_list.json} | 0 ...an_policy_object_security_protocol_list.go | 133 +++++++++ ...licy_object_security_protocol_list_test.go | 81 ++++++ ...an_policy_object_security_protocol_list.go | 178 ++++++++++++ internal/provider/provider.go | 2 + ...an_policy_object_security_protocol_list.go | 257 ++++++++++++++++++ ...licy_object_security_protocol_list_test.go | 79 ++++++ templates/guides/changelog.md.tmpl | 1 + 16 files changed, 880 insertions(+) create mode 100644 docs/data-sources/policy_object_security_protocol_list.md create mode 100644 docs/resources/policy_object_security_protocol_list.md create mode 100644 examples/data-sources/sdwan_policy_object_security_protocol_list/data-source.tf create mode 100644 examples/resources/sdwan_policy_object_security_protocol_list/import.sh create mode 100644 examples/resources/sdwan_policy_object_security_protocol_list/resource.tf create mode 100644 gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml rename gen/models/profile_parcels/{policy_object_security_protocolname.json => policy_object_security_protocol_list.json} (100%) create mode 100644 internal/provider/data_source_sdwan_policy_object_security_protocol_list.go create mode 100644 internal/provider/data_source_sdwan_policy_object_security_protocol_list_test.go create mode 100644 internal/provider/model_sdwan_policy_object_security_protocol_list.go create mode 100644 internal/provider/resource_sdwan_policy_object_security_protocol_list.go create mode 100644 internal/provider/resource_sdwan_policy_object_security_protocol_list_test.go diff --git a/CHANGELOG.md b/CHANGELOG.md index 9879bbbc..20109a51 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -31,6 +31,7 @@ - Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source - Add `sdwan_policy_object_unified_advanced_inspection_profile` resource and data source - Add `sdwan_policy_object_unified_tls_ssl_decryption` resource and data source +- Add `sdwan_policy_object_security_protocol_list` resource and data source ## 0.4.1 diff --git a/docs/data-sources/policy_object_security_protocol_list.md b/docs/data-sources/policy_object_security_protocol_list.md new file mode 100644 index 00000000..93a054d3 --- /dev/null +++ b/docs/data-sources/policy_object_security_protocol_list.md @@ -0,0 +1,42 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_security_protocol_list Data Source - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This data source can read the Policy Object Security Protocol List Policy_object. +--- + +# sdwan_policy_object_security_protocol_list (Data Source) + +This data source can read the Policy Object Security Protocol List Policy_object. + +## Example Usage + +```terraform +data "sdwan_policy_object_security_protocol_list" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} +``` + + +## Schema + +### Required + +- `feature_profile_id` (String) Feature Profile ID +- `id` (String) The id of the Policy_object + +### Read-Only + +- `description` (String) The description of the Policy_object +- `entries` (Attributes List) (see [below for nested schema](#nestedatt--entries)) +- `name` (String) The name of the Policy_object +- `version` (Number) The version of the Policy_object + + +### Nested Schema for `entries` + +Read-Only: + +- `protocol_names` (String) diff --git a/docs/guides/changelog.md b/docs/guides/changelog.md index 452efa62..9de35d85 100644 --- a/docs/guides/changelog.md +++ b/docs/guides/changelog.md @@ -40,6 +40,7 @@ description: |- - Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source - Add `sdwan_policy_object_unified_advanced_inspection_profile` resource and data source - Add `sdwan_policy_object_unified_tls_ssl_decryption` resource and data source +- Add `sdwan_policy_object_security_protocol_list` resource and data source ## 0.4.1 diff --git a/docs/resources/policy_object_security_protocol_list.md b/docs/resources/policy_object_security_protocol_list.md new file mode 100644 index 00000000..83f3c7c5 --- /dev/null +++ b/docs/resources/policy_object_security_protocol_list.md @@ -0,0 +1,61 @@ +--- +# generated by https://github.com/hashicorp/terraform-plugin-docs +page_title: "sdwan_policy_object_security_protocol_list Resource - terraform-provider-sdwan" +subcategory: "Policy Objects" +description: |- + This resource can manage a Policy Object Security Protocol List Policy_object. + Minimum SD-WAN Manager version: 20.12.0 +--- + +# sdwan_policy_object_security_protocol_list (Resource) + +This resource can manage a Policy Object Security Protocol List Policy_object. + - Minimum SD-WAN Manager version: `20.12.0` + +## Example Usage + +```terraform +resource "sdwan_policy_object_security_protocol_list" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + entries = [ + { + protocol_names = "aol" + } + ] +} +``` + + +## Schema + +### Required + +- `entries` (Attributes List) (see [below for nested schema](#nestedatt--entries)) +- `feature_profile_id` (String) Feature Profile ID +- `name` (String) The name of the Policy_object + +### Optional + +- `description` (String) The description of the Policy_object + +### Read-Only + +- `id` (String) The id of the Policy_object +- `version` (Number) The version of the Policy_object + + +### Nested Schema for `entries` + +Optional: + +- `protocol_names` (String) - Choices: `snmp`, `icmp`, `tcp`, `udp`, `echo`, `telnet`, `wins`, `n2h2server`, `nntp`, `pptp`, `rtsp`, `bootpc`, `gdoi`, `tacacs`, `gopher`, `icabrowser`, `skinny`, `sunrpc`, `biff`, `router`, `ircs`, `orasrv`, `ms-cluster-net`, `kermit`, `isakmp`, `sshell`, `realsecure`, `ircu`, `appleqtc`, `pwdgen`, `rdb-dbs-disp`, `creativepartnr`, `finger`, `ftps`, `giop`, `rsvd`, `hp-alarm-mgr`, `uucp`, `kerberos`, `imap`, `time`, `bootps`, `tftp`, `oracle`, `snmptrap`, `http`, `qmtp`, `radius`, `oracle-em-vp`, `tarantella`, `pcanywheredata`, `ldap`, `mgcp`, `sqlsrv`, `hsrp`, `cisco-net-mgmt`, `smtp`, `pcanywherestat`, `exec`, `send`, `stun`, `syslog`, `ms-sql-m`, `citrix`, `creativeserver`, `cifs`, `cisco-sys`, `cisco-tna`, `ms-dotnetster`, `gtpv1`, `gtpv0`, `imap3`, `fcip-port`, `netbios-dgm`, `sip-tls`, `pop3s`, `cisco-fna`, `802-11-iapp`, `oem-agent`, `cisco-tdp`, `tr-rsrb`, `r-winsock`, `sql-net`, `syslog-conn`, `tacacs-ds`, `h225ras`, `ace-svr`, `dhcp-failover`, `igmpv3lite`, `irc-serv`, `entrust-svcs`, `dbcontrol_agent`, `cisco-svcs`, `ipsec-msft`, `microsoft-ds`, `ms-sna`, `rsvp_tunnel`, `rsvp-encap`, `hp-collector`, `netbios-ns`, `msexch-routing`, `h323`, `l2tp`, `ldap-admin`, `pop3`, `h323callsigalt`, `ms-sql`, `iscsi-target`, `webster`, `lotusnote`, `ipx`, `entrust-svc-hand`, `citriximaclient`, `rtc-pm-port`, `ftp`, `aol`, `xdmcp`, `oraclenames`, `login`, `iscsi`, `ttc`, `imaps`, `socks`, `ssh`, `dnsix`, `daytime`, `sip`, `discard`, `ntp`, `ldaps`, `https`, `vdolive`, `ica`, `net8-cman`, `cuseeme`, `netstat`, `sms`, `streamworks`, `rtelnet`, `who`, `kazaa`, `ssp`, `dbase`, `timed`, `cddbp`, `telnets`, `ymsgr`, `ident`, `bgp`, `ddns-v3`, `vqp`, `irc`, `ipass`, `x11`, `dns`, `lotusmtap`, `mysql`, `nfs`, `msnmsgr`, `netshow`, `sqlserv`, `hp-managed-node`, `ncp`, `shell`, `realmedia`, `msrpc`, `clp` + +## Import + +Import is supported using the following syntax: + +```shell +terraform import sdwan_policy_object_security_protocol_list.example "f6b2c44c-693c-4763-b010-895aa3d236bd" +``` diff --git a/examples/data-sources/sdwan_policy_object_security_protocol_list/data-source.tf b/examples/data-sources/sdwan_policy_object_security_protocol_list/data-source.tf new file mode 100644 index 00000000..8982518c --- /dev/null +++ b/examples/data-sources/sdwan_policy_object_security_protocol_list/data-source.tf @@ -0,0 +1,4 @@ +data "sdwan_policy_object_security_protocol_list" "example" { + id = "f6b2c44c-693c-4763-b010-895aa3d236bd" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" +} diff --git a/examples/resources/sdwan_policy_object_security_protocol_list/import.sh b/examples/resources/sdwan_policy_object_security_protocol_list/import.sh new file mode 100644 index 00000000..a3722f52 --- /dev/null +++ b/examples/resources/sdwan_policy_object_security_protocol_list/import.sh @@ -0,0 +1 @@ +terraform import sdwan_policy_object_security_protocol_list.example "f6b2c44c-693c-4763-b010-895aa3d236bd" diff --git a/examples/resources/sdwan_policy_object_security_protocol_list/resource.tf b/examples/resources/sdwan_policy_object_security_protocol_list/resource.tf new file mode 100644 index 00000000..d19b8042 --- /dev/null +++ b/examples/resources/sdwan_policy_object_security_protocol_list/resource.tf @@ -0,0 +1,10 @@ +resource "sdwan_policy_object_security_protocol_list" "example" { + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + entries = [ + { + protocol_names = "aol" + } + ] +} diff --git a/gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml b/gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml new file mode 100644 index 00000000..023636c4 --- /dev/null +++ b/gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml @@ -0,0 +1,29 @@ +--- +name: Policy Object Security Protocol List +rest_endpoint: /v1/feature-profile/sdwan/policy-object/%v/security-protocolname +minimum_version: 20.12.0 +test_tags: [SDWAN_2012] +skip_minimum_test: true +parcel_type: policy_object +attributes: + - tf_name: feature_profile_id + reference: true + type: String + mandatory: true + description: Feature Profile ID + example: f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac + test_value: sdwan_policy_object_feature_profile.test.id + - model_name: entries + mandatory: true + attributes: + - model_name: protocolName + tf_name: protocol_names + id: true + mandatory: true + example: aol + +test_prerequisites: | + resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" + } \ No newline at end of file diff --git a/gen/models/profile_parcels/policy_object_security_protocolname.json b/gen/models/profile_parcels/policy_object_security_protocol_list.json similarity index 100% rename from gen/models/profile_parcels/policy_object_security_protocolname.json rename to gen/models/profile_parcels/policy_object_security_protocol_list.json diff --git a/internal/provider/data_source_sdwan_policy_object_security_protocol_list.go b/internal/provider/data_source_sdwan_policy_object_security_protocol_list.go new file mode 100644 index 00000000..9c9cf9a8 --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_security_protocol_list.go @@ -0,0 +1,133 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/hashicorp/terraform-plugin-framework/datasource" + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure the implementation satisfies the expected interfaces. +var ( + _ datasource.DataSource = &PolicyObjectSecurityProtocolListProfileParcelDataSource{} + _ datasource.DataSourceWithConfigure = &PolicyObjectSecurityProtocolListProfileParcelDataSource{} +) + +func NewPolicyObjectSecurityProtocolListProfileParcelDataSource() datasource.DataSource { + return &PolicyObjectSecurityProtocolListProfileParcelDataSource{} +} + +type PolicyObjectSecurityProtocolListProfileParcelDataSource struct { + client *sdwan.Client +} + +func (d *PolicyObjectSecurityProtocolListProfileParcelDataSource) Metadata(_ context.Context, req datasource.MetadataRequest, resp *datasource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_security_protocol_list" +} + +func (d *PolicyObjectSecurityProtocolListProfileParcelDataSource) Schema(ctx context.Context, req datasource.SchemaRequest, resp *datasource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: "This data source can read the Policy Object Security Protocol List Policy_object.", + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Required: true, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Computed: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Computed: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: "Feature Profile ID", + Required: true, + }, + "entries": schema.ListNestedAttribute{ + MarkdownDescription: "", + Computed: true, + NestedObject: schema.NestedAttributeObject{ + Attributes: map[string]schema.Attribute{ + "protocol_names": schema.StringAttribute{ + MarkdownDescription: "", + Computed: true, + }, + }, + }, + }, + }, + } +} + +func (d *PolicyObjectSecurityProtocolListProfileParcelDataSource) Configure(_ context.Context, req datasource.ConfigureRequest, _ *datasource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + d.client = req.ProviderData.(*SdwanProviderData).Client +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (d *PolicyObjectSecurityProtocolListProfileParcelDataSource) Read(ctx context.Context, req datasource.ReadRequest, resp *datasource.ReadResponse) { + var config PolicyObjectSecurityProtocolList + + // Read config + diags := req.Config.Get(ctx, &config) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", config.Id.String())) + + res, err := d.client.Get(config.getPath() + "/" + url.QueryEscape(config.Id.ValueString())) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object, got error: %s", err)) + return + } + + config.fromBody(ctx, res) + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", config.Name.ValueString())) + + diags = resp.State.Set(ctx, &config) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read diff --git a/internal/provider/data_source_sdwan_policy_object_security_protocol_list_test.go b/internal/provider/data_source_sdwan_policy_object_security_protocol_list_test.go new file mode 100644 index 00000000..63318c0a --- /dev/null +++ b/internal/provider/data_source_sdwan_policy_object_security_protocol_list_test.go @@ -0,0 +1,81 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSource +func TestAccDataSourceSdwanPolicyObjectSecurityProtocolListProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_security_protocol_list.test", "entries.0.protocol_names", "aol")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + { + Config: testAccDataSourceSdwanPolicyObjectSecurityProtocolListPrerequisitesProfileParcelConfig + testAccDataSourceSdwanPolicyObjectSecurityProtocolListProfileParcelConfig(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAccDataSource + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccDataSourceSdwanPolicyObjectSecurityProtocolListPrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccDataSourceConfig +func testAccDataSourceSdwanPolicyObjectSecurityProtocolListProfileParcelConfig() string { + config := `resource "sdwan_policy_object_security_protocol_list" "test" {` + "\n" + config += ` name = "TF_TEST"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` entries = [{` + "\n" + config += ` protocol_names = "aol"` + "\n" + config += ` }]` + "\n" + config += `}` + "\n" + + config += ` + data "sdwan_policy_object_security_protocol_list" "test" { + id = sdwan_policy_object_security_protocol_list.test.id + feature_profile_id = sdwan_policy_object_feature_profile.test.id + } + ` + return config +} + +// End of section. //template:end testAccDataSourceConfig diff --git a/internal/provider/model_sdwan_policy_object_security_protocol_list.go b/internal/provider/model_sdwan_policy_object_security_protocol_list.go new file mode 100644 index 00000000..faa1fb3c --- /dev/null +++ b/internal/provider/model_sdwan_policy_object_security_protocol_list.go @@ -0,0 +1,178 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/tidwall/gjson" + "github.com/tidwall/sjson" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin types +type PolicyObjectSecurityProtocolList struct { + Id types.String `tfsdk:"id"` + Version types.Int64 `tfsdk:"version"` + Name types.String `tfsdk:"name"` + Description types.String `tfsdk:"description"` + FeatureProfileId types.String `tfsdk:"feature_profile_id"` + Entries []PolicyObjectSecurityProtocolListEntries `tfsdk:"entries"` +} + +type PolicyObjectSecurityProtocolListEntries struct { + ProtocolNames types.String `tfsdk:"protocol_names"` +} + +// End of section. //template:end types + +// Section below is generated&owned by "gen/generator.go". //template:begin getModel +func (data PolicyObjectSecurityProtocolList) getModel() string { + return "policy_object_security_protocol_list" +} + +// End of section. //template:end getModel + +// Section below is generated&owned by "gen/generator.go". //template:begin getPath +func (data PolicyObjectSecurityProtocolList) getPath() string { + return fmt.Sprintf("/v1/feature-profile/sdwan/policy-object/%v/security-protocolname", url.QueryEscape(data.FeatureProfileId.ValueString())) +} + +// End of section. //template:end getPath + +// Section below is generated&owned by "gen/generator.go". //template:begin toBody +func (data PolicyObjectSecurityProtocolList) toBody(ctx context.Context) string { + body := "" + body, _ = sjson.Set(body, "name", data.Name.ValueString()) + body, _ = sjson.Set(body, "description", data.Description.ValueString()) + path := "data." + if true { + + for _, item := range data.Entries { + itemBody := "" + if !item.ProtocolNames.IsNull() { + if true { + itemBody, _ = sjson.Set(itemBody, "protocolName.optionType", "global") + itemBody, _ = sjson.Set(itemBody, "protocolName.value", item.ProtocolNames.ValueString()) + } + } + body, _ = sjson.SetRaw(body, path+"entries.-1", itemBody) + } + } + return body +} + +// End of section. //template:end toBody + +// Section below is generated&owned by "gen/generator.go". //template:begin fromBody +func (data *PolicyObjectSecurityProtocolList) fromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + if value := res.Get(path + "entries"); value.Exists() { + data.Entries = make([]PolicyObjectSecurityProtocolListEntries, 0) + value.ForEach(func(k, v gjson.Result) bool { + item := PolicyObjectSecurityProtocolListEntries{} + item.ProtocolNames = types.StringNull() + + if t := v.Get("protocolName.optionType"); t.Exists() { + va := v.Get("protocolName.value") + if t.String() == "global" { + item.ProtocolNames = types.StringValue(va.String()) + } + } + data.Entries = append(data.Entries, item) + return true + }) + } +} + +// End of section. //template:end fromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin updateFromBody +func (data *PolicyObjectSecurityProtocolList) updateFromBody(ctx context.Context, res gjson.Result) { + data.Name = types.StringValue(res.Get("payload.name").String()) + if value := res.Get("payload.description"); value.Exists() && value.String() != "" { + data.Description = types.StringValue(value.String()) + } else { + data.Description = types.StringNull() + } + path := "payload.data." + for i := range data.Entries { + keys := [...]string{"protocolName"} + keyValues := [...]string{data.Entries[i].ProtocolNames.ValueString()} + keyValuesVariables := [...]string{""} + + var r gjson.Result + res.Get(path + "entries").ForEach( + func(_, v gjson.Result) bool { + found := false + for ik := range keys { + tt := v.Get(keys[ik] + ".optionType") + vv := v.Get(keys[ik] + ".value") + if tt.Exists() && vv.Exists() { + if (tt.String() == "variable" && vv.String() == keyValuesVariables[ik]) || (tt.String() == "global" && vv.String() == keyValues[ik]) { + found = true + continue + } + found = false + break + } + continue + } + if found { + r = v + return false + } + return true + }, + ) + data.Entries[i].ProtocolNames = types.StringNull() + + if t := r.Get("protocolName.optionType"); t.Exists() { + va := r.Get("protocolName.value") + if t.String() == "global" { + data.Entries[i].ProtocolNames = types.StringValue(va.String()) + } + } + } +} + +// End of section. //template:end updateFromBody + +// Section below is generated&owned by "gen/generator.go". //template:begin isNull +func (data *PolicyObjectSecurityProtocolList) isNull(ctx context.Context, res gjson.Result) bool { + if !data.FeatureProfileId.IsNull() { + return false + } + if len(data.Entries) > 0 { + return false + } + return true +} + +// End of section. //template:end isNull diff --git a/internal/provider/provider.go b/internal/provider/provider.go index a7d11d59..0befe8e0 100644 --- a/internal/provider/provider.go +++ b/internal/provider/provider.go @@ -307,6 +307,7 @@ func (p *SdwanProvider) Resources(ctx context.Context) []func() resource.Resourc NewPolicyObjectSecurityLocalApplicationListProfileParcelResource, NewPolicyObjectSecurityLocalDomainListProfileParcelResource, NewPolicyObjectSecurityPortListProfileParcelResource, + NewPolicyObjectSecurityProtocolListProfileParcelResource, NewPolicyObjectSecurityScalableGroupTagListProfileParcelResource, NewPolicyObjectSecurityURLAllowListProfileParcelResource, NewPolicyObjectSecurityURLBlockListProfileParcelResource, @@ -517,6 +518,7 @@ func (p *SdwanProvider) DataSources(ctx context.Context) []func() datasource.Dat NewPolicyObjectSecurityLocalApplicationListProfileParcelDataSource, NewPolicyObjectSecurityLocalDomainListProfileParcelDataSource, NewPolicyObjectSecurityPortListProfileParcelDataSource, + NewPolicyObjectSecurityProtocolListProfileParcelDataSource, NewPolicyObjectSecurityScalableGroupTagListProfileParcelDataSource, NewPolicyObjectSecurityURLAllowListProfileParcelDataSource, NewPolicyObjectSecurityURLBlockListProfileParcelDataSource, diff --git a/internal/provider/resource_sdwan_policy_object_security_protocol_list.go b/internal/provider/resource_sdwan_policy_object_security_protocol_list.go new file mode 100644 index 00000000..a1c13e47 --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_security_protocol_list.go @@ -0,0 +1,257 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "context" + "fmt" + "net/url" + "sync" + + "github.com/CiscoDevNet/terraform-provider-sdwan/internal/provider/helpers" + "github.com/hashicorp/terraform-plugin-framework-validators/stringvalidator" + "github.com/hashicorp/terraform-plugin-framework/path" + "github.com/hashicorp/terraform-plugin-framework/resource" + "github.com/hashicorp/terraform-plugin-framework/resource/schema" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/planmodifier" + "github.com/hashicorp/terraform-plugin-framework/resource/schema/stringplanmodifier" + "github.com/hashicorp/terraform-plugin-framework/schema/validator" + "github.com/hashicorp/terraform-plugin-framework/types" + "github.com/hashicorp/terraform-plugin-log/tflog" + "github.com/netascode/go-sdwan" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin model + +// Ensure provider defined types fully satisfy framework interfaces +var _ resource.Resource = &PolicyObjectSecurityProtocolListProfileParcelResource{} +var _ resource.ResourceWithImportState = &PolicyObjectSecurityProtocolListProfileParcelResource{} + +func NewPolicyObjectSecurityProtocolListProfileParcelResource() resource.Resource { + return &PolicyObjectSecurityProtocolListProfileParcelResource{} +} + +type PolicyObjectSecurityProtocolListProfileParcelResource struct { + client *sdwan.Client + updateMutex *sync.Mutex +} + +func (r *PolicyObjectSecurityProtocolListProfileParcelResource) Metadata(ctx context.Context, req resource.MetadataRequest, resp *resource.MetadataResponse) { + resp.TypeName = req.ProviderTypeName + "_policy_object_security_protocol_list" +} + +func (r *PolicyObjectSecurityProtocolListProfileParcelResource) Schema(ctx context.Context, req resource.SchemaRequest, resp *resource.SchemaResponse) { + resp.Schema = schema.Schema{ + // This description is used by the documentation generator and the language server. + MarkdownDescription: helpers.NewAttributeDescription("This resource can manage a Policy Object Security Protocol List Policy_object.").AddMinimumVersionDescription("20.12.0").String, + + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + MarkdownDescription: "The id of the Policy_object", + Computed: true, + PlanModifiers: []planmodifier.String{ + stringplanmodifier.UseStateForUnknown(), + }, + }, + "version": schema.Int64Attribute{ + MarkdownDescription: "The version of the Policy_object", + Computed: true, + }, + "name": schema.StringAttribute{ + MarkdownDescription: "The name of the Policy_object", + Required: true, + }, + "description": schema.StringAttribute{ + MarkdownDescription: "The description of the Policy_object", + Optional: true, + }, + "feature_profile_id": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("Feature Profile ID").String, + Required: true, + }, + "entries": schema.ListNestedAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").String, + Required: true, + NestedObject: schema.NestedAttributeObject{ + Attributes: map[string]schema.Attribute{ + "protocol_names": schema.StringAttribute{ + MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("snmp", "icmp", "tcp", "udp", "echo", "telnet", "wins", "n2h2server", "nntp", "pptp", "rtsp", "bootpc", "gdoi", "tacacs", "gopher", "icabrowser", "skinny", "sunrpc", "biff", "router", "ircs", "orasrv", "ms-cluster-net", "kermit", "isakmp", "sshell", "realsecure", "ircu", "appleqtc", "pwdgen", "rdb-dbs-disp", "creativepartnr", "finger", "ftps", "giop", "rsvd", "hp-alarm-mgr", "uucp", "kerberos", "imap", "time", "bootps", "tftp", "oracle", "snmptrap", "http", "qmtp", "radius", "oracle-em-vp", "tarantella", "pcanywheredata", "ldap", "mgcp", "sqlsrv", "hsrp", "cisco-net-mgmt", "smtp", "pcanywherestat", "exec", "send", "stun", "syslog", "ms-sql-m", "citrix", "creativeserver", "cifs", "cisco-sys", "cisco-tna", "ms-dotnetster", "gtpv1", "gtpv0", "imap3", "fcip-port", "netbios-dgm", "sip-tls", "pop3s", "cisco-fna", "802-11-iapp", "oem-agent", "cisco-tdp", "tr-rsrb", "r-winsock", "sql-net", "syslog-conn", "tacacs-ds", "h225ras", "ace-svr", "dhcp-failover", "igmpv3lite", "irc-serv", "entrust-svcs", "dbcontrol_agent", "cisco-svcs", "ipsec-msft", "microsoft-ds", "ms-sna", "rsvp_tunnel", "rsvp-encap", "hp-collector", "netbios-ns", "msexch-routing", "h323", "l2tp", "ldap-admin", "pop3", "h323callsigalt", "ms-sql", "iscsi-target", "webster", "lotusnote", "ipx", "entrust-svc-hand", "citriximaclient", "rtc-pm-port", "ftp", "aol", "xdmcp", "oraclenames", "login", "iscsi", "ttc", "imaps", "socks", "ssh", "dnsix", "daytime", "sip", "discard", "ntp", "ldaps", "https", "vdolive", "ica", "net8-cman", "cuseeme", "netstat", "sms", "streamworks", "rtelnet", "who", "kazaa", "ssp", "dbase", "timed", "cddbp", "telnets", "ymsgr", "ident", "bgp", "ddns-v3", "vqp", "irc", "ipass", "x11", "dns", "lotusmtap", "mysql", "nfs", "msnmsgr", "netshow", "sqlserv", "hp-managed-node", "ncp", "shell", "realmedia", "msrpc", "clp").String, + Optional: true, + Validators: []validator.String{ + stringvalidator.OneOf("snmp", "icmp", "tcp", "udp", "echo", "telnet", "wins", "n2h2server", "nntp", "pptp", "rtsp", "bootpc", "gdoi", "tacacs", "gopher", "icabrowser", "skinny", "sunrpc", "biff", "router", "ircs", "orasrv", "ms-cluster-net", "kermit", "isakmp", "sshell", "realsecure", "ircu", "appleqtc", "pwdgen", "rdb-dbs-disp", "creativepartnr", "finger", "ftps", "giop", "rsvd", "hp-alarm-mgr", "uucp", "kerberos", "imap", "time", "bootps", "tftp", "oracle", "snmptrap", "http", "qmtp", "radius", "oracle-em-vp", "tarantella", "pcanywheredata", "ldap", "mgcp", "sqlsrv", "hsrp", "cisco-net-mgmt", "smtp", "pcanywherestat", "exec", "send", "stun", "syslog", "ms-sql-m", "citrix", "creativeserver", "cifs", "cisco-sys", "cisco-tna", "ms-dotnetster", "gtpv1", "gtpv0", "imap3", "fcip-port", "netbios-dgm", "sip-tls", "pop3s", "cisco-fna", "802-11-iapp", "oem-agent", "cisco-tdp", "tr-rsrb", "r-winsock", "sql-net", "syslog-conn", "tacacs-ds", "h225ras", "ace-svr", "dhcp-failover", "igmpv3lite", "irc-serv", "entrust-svcs", "dbcontrol_agent", "cisco-svcs", "ipsec-msft", "microsoft-ds", "ms-sna", "rsvp_tunnel", "rsvp-encap", "hp-collector", "netbios-ns", "msexch-routing", "h323", "l2tp", "ldap-admin", "pop3", "h323callsigalt", "ms-sql", "iscsi-target", "webster", "lotusnote", "ipx", "entrust-svc-hand", "citriximaclient", "rtc-pm-port", "ftp", "aol", "xdmcp", "oraclenames", "login", "iscsi", "ttc", "imaps", "socks", "ssh", "dnsix", "daytime", "sip", "discard", "ntp", "ldaps", "https", "vdolive", "ica", "net8-cman", "cuseeme", "netstat", "sms", "streamworks", "rtelnet", "who", "kazaa", "ssp", "dbase", "timed", "cddbp", "telnets", "ymsgr", "ident", "bgp", "ddns-v3", "vqp", "irc", "ipass", "x11", "dns", "lotusmtap", "mysql", "nfs", "msnmsgr", "netshow", "sqlserv", "hp-managed-node", "ncp", "shell", "realmedia", "msrpc", "clp"), + }, + }, + }, + }, + }, + }, + } +} + +func (r *PolicyObjectSecurityProtocolListProfileParcelResource) Configure(_ context.Context, req resource.ConfigureRequest, _ *resource.ConfigureResponse) { + if req.ProviderData == nil { + return + } + + r.client = req.ProviderData.(*SdwanProviderData).Client + r.updateMutex = req.ProviderData.(*SdwanProviderData).UpdateMutex +} + +// End of section. //template:end model + +// Section below is generated&owned by "gen/generator.go". //template:begin create +func (r *PolicyObjectSecurityProtocolListProfileParcelResource) Create(ctx context.Context, req resource.CreateRequest, resp *resource.CreateResponse) { + var plan PolicyObjectSecurityProtocolList + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Create", plan.Name.ValueString())) + + // Create object + body := plan.toBody(ctx) + + res, err := r.client.Post(plan.getPath(), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (POST), got error: %s, %s", err, res.String())) + return + } + + plan.Id = types.StringValue(res.Get("parcelId").String()) + plan.Version = types.Int64Value(0) + + tflog.Debug(ctx, fmt.Sprintf("%s: Create finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end create + +// Section below is generated&owned by "gen/generator.go". //template:begin read +func (r *PolicyObjectSecurityProtocolListProfileParcelResource) Read(ctx context.Context, req resource.ReadRequest, resp *resource.ReadResponse) { + var state PolicyObjectSecurityProtocolList + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Read", state.Name.String())) + + res, err := r.client.Get(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if res.Get("error.message").String() == "Invalid feature Id" { + resp.State.RemoveResource(ctx) + return + } else if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to retrieve object (GET), got error: %s, %s", err, res.String())) + return + } + + // If every attribute is set to null we are dealing with an import operation and therefore reading all attributes + if state.isNull(ctx, res) { + state.fromBody(ctx, res) + } else { + state.updateFromBody(ctx, res) + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Read finished successfully", state.Name.ValueString())) + + diags = resp.State.Set(ctx, &state) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end read + +// Section below is generated&owned by "gen/generator.go". //template:begin update +func (r *PolicyObjectSecurityProtocolListProfileParcelResource) Update(ctx context.Context, req resource.UpdateRequest, resp *resource.UpdateResponse) { + var plan, state PolicyObjectSecurityProtocolList + + // Read plan + diags := req.Plan.Get(ctx, &plan) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + // Read state + diags = req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Update", plan.Name.ValueString())) + + body := plan.toBody(ctx) + res, err := r.client.Put(plan.getPath()+"/"+url.QueryEscape(plan.Id.ValueString()), body) + if err != nil { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to configure object (PUT), got error: %s, %s", err, res.String())) + return + } + + plan.Version = types.Int64Value(state.Version.ValueInt64() + 1) + + tflog.Debug(ctx, fmt.Sprintf("%s: Update finished successfully", plan.Name.ValueString())) + + diags = resp.State.Set(ctx, &plan) + resp.Diagnostics.Append(diags...) +} + +// End of section. //template:end update + +// Section below is generated&owned by "gen/generator.go". //template:begin delete +func (r *PolicyObjectSecurityProtocolListProfileParcelResource) Delete(ctx context.Context, req resource.DeleteRequest, resp *resource.DeleteResponse) { + var state PolicyObjectSecurityProtocolList + + // Read state + diags := req.State.Get(ctx, &state) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Beginning Delete", state.Name.ValueString())) + + res, err := r.client.Delete(state.getPath() + "/" + url.QueryEscape(state.Id.ValueString())) + if err != nil && res.Get("error.message").String() != "Invalid Template Id" { + resp.Diagnostics.AddError("Client Error", fmt.Sprintf("Failed to delete object (DELETE), got error: %s, %s", err, res.String())) + return + } + + tflog.Debug(ctx, fmt.Sprintf("%s: Delete finished successfully", state.Name.ValueString())) + + resp.State.RemoveResource(ctx) +} + +// End of section. //template:end delete + +// Section below is generated&owned by "gen/generator.go". //template:begin import +func (r *PolicyObjectSecurityProtocolListProfileParcelResource) ImportState(ctx context.Context, req resource.ImportStateRequest, resp *resource.ImportStateResponse) { + resource.ImportStatePassthroughID(ctx, path.Root("id"), req, resp) +} + +// End of section. //template:end import diff --git a/internal/provider/resource_sdwan_policy_object_security_protocol_list_test.go b/internal/provider/resource_sdwan_policy_object_security_protocol_list_test.go new file mode 100644 index 00000000..70a2e6f1 --- /dev/null +++ b/internal/provider/resource_sdwan_policy_object_security_protocol_list_test.go @@ -0,0 +1,79 @@ +// Copyright © 2023 Cisco Systems, Inc. and its affiliates. +// All rights reserved. +// +// Licensed under the Mozilla Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// https://mozilla.org/MPL/2.0/ +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +// SPDX-License-Identifier: MPL-2.0 + +package provider + +// Section below is generated&owned by "gen/generator.go". //template:begin imports +import ( + "os" + "testing" + + "github.com/hashicorp/terraform-plugin-testing/helper/resource" +) + +// End of section. //template:end imports + +// Section below is generated&owned by "gen/generator.go". //template:begin testAcc +func TestAccSdwanPolicyObjectSecurityProtocolListProfileParcel(t *testing.T) { + if os.Getenv("SDWAN_2012") == "" { + t.Skip("skipping test, set environment variable SDWAN_2012") + } + var checks []resource.TestCheckFunc + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_security_protocol_list.test", "entries.0.protocol_names", "aol")) + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, + Steps: []resource.TestStep{ + + { + Config: testAccSdwanPolicyObjectSecurityProtocolListPrerequisitesProfileParcelConfig + testAccSdwanPolicyObjectSecurityProtocolListProfileParcelConfig_all(), + Check: resource.ComposeTestCheckFunc(checks...), + }, + }, + }) +} + +// End of section. //template:end testAcc + +// Section below is generated&owned by "gen/generator.go". //template:begin testPrerequisites +const testAccSdwanPolicyObjectSecurityProtocolListPrerequisitesProfileParcelConfig = ` +resource "sdwan_policy_object_feature_profile" "test" { + name = "POLICY_OBJECT_FP_1" + description = "My policy object feature profile 1" +} +` + +// End of section. //template:end testPrerequisites + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigMinimum + +// End of section. //template:end testAccConfigMinimum + +// Section below is generated&owned by "gen/generator.go". //template:begin testAccConfigAll +func testAccSdwanPolicyObjectSecurityProtocolListProfileParcelConfig_all() string { + config := `resource "sdwan_policy_object_security_protocol_list" "test" {` + "\n" + config += ` name = "TF_TEST_ALL"` + "\n" + config += ` description = "Terraform integration test"` + "\n" + config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" + config += ` entries = [{` + "\n" + config += ` protocol_names = "aol"` + "\n" + config += ` }]` + "\n" + config += `}` + "\n" + return config +} + +// End of section. //template:end testAccConfigAll diff --git a/templates/guides/changelog.md.tmpl b/templates/guides/changelog.md.tmpl index 452efa62..9de35d85 100644 --- a/templates/guides/changelog.md.tmpl +++ b/templates/guides/changelog.md.tmpl @@ -40,6 +40,7 @@ description: |- - Add `sdwan_policy_object_unified_intrusion_prevention` resource and data source - Add `sdwan_policy_object_unified_advanced_inspection_profile` resource and data source - Add `sdwan_policy_object_unified_tls_ssl_decryption` resource and data source +- Add `sdwan_policy_object_security_protocol_list` resource and data source ## 0.4.1 From ce4593b33bec1b9952982de88b40d1c3943411fe Mon Sep 17 00:00:00 2001 From: Sean Conroy Date: Tue, 19 Nov 2024 11:27:05 +0000 Subject: [PATCH 09/11] Resolve comments --- .../policy_object_security_protocol_list.md | 2 +- ...ect_unified_advanced_malware_protection.md | 1 - ...icy_object_unified_intrusion_prevention.md | 2 +- ...olicy_object_unified_tls_ssl_decryption.md | 1 - .../policy_object_security_protocol_list.md | 4 +-- ...ect_unified_advanced_inspection_profile.md | 8 ++--- ...ect_unified_advanced_malware_protection.md | 10 +++--- ...icy_object_unified_intrusion_prevention.md | 20 +++++------ ...olicy_object_unified_tls_ssl_decryption.md | 8 ++--- .../policy_object_unified_tls_ssl_profile.md | 10 +++--- .../policy_object_unified_url_filtering.md | 11 +++--- .../resource.tf | 2 +- .../resource.tf | 1 - .../resource.tf | 16 ++++----- .../resource.tf | 3 +- .../resource.tf | 1 - .../policy_object_security_protocol_list.yaml | 2 +- ...t_unified_advanced_inspection_profile.yaml | 5 ++- ...t_unified_advanced_malware_protection.yaml | 21 ++++++++++++ ...y_object_unified_intrusion_prevention.yaml | 4 ++- ...icy_object_unified_tls_ssl_decryption.yaml | 19 ++++++++++- ...policy_object_unified_tls_ssl_profile.yaml | 12 +++++++ .../policy_object_unified_url_filtering.yaml | 21 ++++++++++++ gen/generator.go | 7 +++- gen/schema/schema.yaml | 2 ++ gen/templates/profile_parcels/model.go | 8 ++--- ...an_policy_object_security_protocol_list.go | 2 +- ...licy_object_security_protocol_list_test.go | 4 +-- ...nified_advanced_inspection_profile_test.go | 1 - ...ect_unified_advanced_malware_protection.go | 4 --- ...nified_advanced_malware_protection_test.go | 2 -- ...icy_object_unified_intrusion_prevention.go | 2 +- ...bject_unified_intrusion_prevention_test.go | 2 +- ...olicy_object_unified_tls_ssl_decryption.go | 4 --- ..._object_unified_tls_ssl_decryption_test.go | 6 ++-- ...olicy_object_unified_url_filtering_test.go | 2 -- ...an_policy_object_security_protocol_list.go | 16 ++++----- ...ect_unified_advanced_malware_protection.go | 34 ++++--------------- ...icy_object_unified_intrusion_prevention.go | 34 +++++++++---------- ...olicy_object_unified_tls_ssl_decryption.go | 30 +++------------- ...n_policy_object_unified_tls_ssl_profile.go | 4 +-- ...wan_policy_object_unified_url_filtering.go | 6 ++-- ...an_policy_object_security_protocol_list.go | 2 +- ...licy_object_security_protocol_list_test.go | 4 +-- ...ect_unified_advanced_inspection_profile.go | 8 ++--- ...nified_advanced_inspection_profile_test.go | 1 - ...ect_unified_advanced_malware_protection.go | 16 ++++----- ...nified_advanced_malware_protection_test.go | 2 -- ...icy_object_unified_intrusion_prevention.go | 6 ++-- ...bject_unified_intrusion_prevention_test.go | 2 +- ...olicy_object_unified_tls_ssl_decryption.go | 8 ++--- ..._object_unified_tls_ssl_decryption_test.go | 6 ++-- ...n_policy_object_unified_tls_ssl_profile.go | 12 +++---- ...wan_policy_object_unified_url_filtering.go | 16 ++++----- ...olicy_object_unified_url_filtering_test.go | 2 -- 55 files changed, 221 insertions(+), 218 deletions(-) diff --git a/docs/data-sources/policy_object_security_protocol_list.md b/docs/data-sources/policy_object_security_protocol_list.md index 93a054d3..da078f1d 100644 --- a/docs/data-sources/policy_object_security_protocol_list.md +++ b/docs/data-sources/policy_object_security_protocol_list.md @@ -39,4 +39,4 @@ data "sdwan_policy_object_security_protocol_list" "example" { Read-Only: -- `protocol_names` (String) +- `protocol_name` (String) diff --git a/docs/data-sources/policy_object_unified_advanced_malware_protection.md b/docs/data-sources/policy_object_unified_advanced_malware_protection.md index 7488853b..1b550ce6 100644 --- a/docs/data-sources/policy_object_unified_advanced_malware_protection.md +++ b/docs/data-sources/policy_object_unified_advanced_malware_protection.md @@ -37,6 +37,5 @@ data "sdwan_policy_object_unified_advanced_malware_protection" "example" { - `file_analysis_alert_log_level` (String) - `file_analysis_cloud_region` (String) - `file_analysis_file_types` (Set of String) -- `match_all_vpn` (Boolean) - `name` (String) The name of the Policy_object - `version` (Number) The version of the Policy_object diff --git a/docs/data-sources/policy_object_unified_intrusion_prevention.md b/docs/data-sources/policy_object_unified_intrusion_prevention.md index b2694adf..7163816c 100644 --- a/docs/data-sources/policy_object_unified_intrusion_prevention.md +++ b/docs/data-sources/policy_object_unified_intrusion_prevention.md @@ -32,7 +32,7 @@ data "sdwan_policy_object_unified_intrusion_prevention" "example" { - `custom_signature` (Boolean) Can be one of the enum value - `description` (String) The description of the Policy_object - `inspection_mode` (String) Can be one of the enum value -- `ips_signature_list_id` (String) +- `ips_signature_allow_list_id` (String) - `log_level` (String) Can be one of the enum value - `name` (String) The name of the Policy_object - `signature_set` (String) Can be one of the enum value diff --git a/docs/data-sources/policy_object_unified_tls_ssl_decryption.md b/docs/data-sources/policy_object_unified_tls_ssl_decryption.md index 3f535ee7..c65afd1d 100644 --- a/docs/data-sources/policy_object_unified_tls_ssl_decryption.md +++ b/docs/data-sources/policy_object_unified_tls_ssl_decryption.md @@ -35,7 +35,6 @@ data "sdwan_policy_object_unified_tls_ssl_decryption" "example" { - `default_ca_certificate_bundle` (Boolean) - `description` (String) The description of the Policy_object - `ec_key_type` (String) -- `enable_ssl` (Boolean) If false, no other fields should be provided, if true all fields should be provided - `expired_certificate` (String) - `failure_mode` (String) - `file_name` (String) diff --git a/docs/resources/policy_object_security_protocol_list.md b/docs/resources/policy_object_security_protocol_list.md index 83f3c7c5..012fc595 100644 --- a/docs/resources/policy_object_security_protocol_list.md +++ b/docs/resources/policy_object_security_protocol_list.md @@ -21,7 +21,7 @@ resource "sdwan_policy_object_security_protocol_list" "example" { feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" entries = [ { - protocol_names = "aol" + protocol_name = "aol" } ] } @@ -50,7 +50,7 @@ resource "sdwan_policy_object_security_protocol_list" "example" { Optional: -- `protocol_names` (String) - Choices: `snmp`, `icmp`, `tcp`, `udp`, `echo`, `telnet`, `wins`, `n2h2server`, `nntp`, `pptp`, `rtsp`, `bootpc`, `gdoi`, `tacacs`, `gopher`, `icabrowser`, `skinny`, `sunrpc`, `biff`, `router`, `ircs`, `orasrv`, `ms-cluster-net`, `kermit`, `isakmp`, `sshell`, `realsecure`, `ircu`, `appleqtc`, `pwdgen`, `rdb-dbs-disp`, `creativepartnr`, `finger`, `ftps`, `giop`, `rsvd`, `hp-alarm-mgr`, `uucp`, `kerberos`, `imap`, `time`, `bootps`, `tftp`, `oracle`, `snmptrap`, `http`, `qmtp`, `radius`, `oracle-em-vp`, `tarantella`, `pcanywheredata`, `ldap`, `mgcp`, `sqlsrv`, `hsrp`, `cisco-net-mgmt`, `smtp`, `pcanywherestat`, `exec`, `send`, `stun`, `syslog`, `ms-sql-m`, `citrix`, `creativeserver`, `cifs`, `cisco-sys`, `cisco-tna`, `ms-dotnetster`, `gtpv1`, `gtpv0`, `imap3`, `fcip-port`, `netbios-dgm`, `sip-tls`, `pop3s`, `cisco-fna`, `802-11-iapp`, `oem-agent`, `cisco-tdp`, `tr-rsrb`, `r-winsock`, `sql-net`, `syslog-conn`, `tacacs-ds`, `h225ras`, `ace-svr`, `dhcp-failover`, `igmpv3lite`, `irc-serv`, `entrust-svcs`, `dbcontrol_agent`, `cisco-svcs`, `ipsec-msft`, `microsoft-ds`, `ms-sna`, `rsvp_tunnel`, `rsvp-encap`, `hp-collector`, `netbios-ns`, `msexch-routing`, `h323`, `l2tp`, `ldap-admin`, `pop3`, `h323callsigalt`, `ms-sql`, `iscsi-target`, `webster`, `lotusnote`, `ipx`, `entrust-svc-hand`, `citriximaclient`, `rtc-pm-port`, `ftp`, `aol`, `xdmcp`, `oraclenames`, `login`, `iscsi`, `ttc`, `imaps`, `socks`, `ssh`, `dnsix`, `daytime`, `sip`, `discard`, `ntp`, `ldaps`, `https`, `vdolive`, `ica`, `net8-cman`, `cuseeme`, `netstat`, `sms`, `streamworks`, `rtelnet`, `who`, `kazaa`, `ssp`, `dbase`, `timed`, `cddbp`, `telnets`, `ymsgr`, `ident`, `bgp`, `ddns-v3`, `vqp`, `irc`, `ipass`, `x11`, `dns`, `lotusmtap`, `mysql`, `nfs`, `msnmsgr`, `netshow`, `sqlserv`, `hp-managed-node`, `ncp`, `shell`, `realmedia`, `msrpc`, `clp` +- `protocol_name` (String) - Choices: `snmp`, `icmp`, `tcp`, `udp`, `echo`, `telnet`, `wins`, `n2h2server`, `nntp`, `pptp`, `rtsp`, `bootpc`, `gdoi`, `tacacs`, `gopher`, `icabrowser`, `skinny`, `sunrpc`, `biff`, `router`, `ircs`, `orasrv`, `ms-cluster-net`, `kermit`, `isakmp`, `sshell`, `realsecure`, `ircu`, `appleqtc`, `pwdgen`, `rdb-dbs-disp`, `creativepartnr`, `finger`, `ftps`, `giop`, `rsvd`, `hp-alarm-mgr`, `uucp`, `kerberos`, `imap`, `time`, `bootps`, `tftp`, `oracle`, `snmptrap`, `http`, `qmtp`, `radius`, `oracle-em-vp`, `tarantella`, `pcanywheredata`, `ldap`, `mgcp`, `sqlsrv`, `hsrp`, `cisco-net-mgmt`, `smtp`, `pcanywherestat`, `exec`, `send`, `stun`, `syslog`, `ms-sql-m`, `citrix`, `creativeserver`, `cifs`, `cisco-sys`, `cisco-tna`, `ms-dotnetster`, `gtpv1`, `gtpv0`, `imap3`, `fcip-port`, `netbios-dgm`, `sip-tls`, `pop3s`, `cisco-fna`, `802-11-iapp`, `oem-agent`, `cisco-tdp`, `tr-rsrb`, `r-winsock`, `sql-net`, `syslog-conn`, `tacacs-ds`, `h225ras`, `ace-svr`, `dhcp-failover`, `igmpv3lite`, `irc-serv`, `entrust-svcs`, `dbcontrol_agent`, `cisco-svcs`, `ipsec-msft`, `microsoft-ds`, `ms-sna`, `rsvp_tunnel`, `rsvp-encap`, `hp-collector`, `netbios-ns`, `msexch-routing`, `h323`, `l2tp`, `ldap-admin`, `pop3`, `h323callsigalt`, `ms-sql`, `iscsi-target`, `webster`, `lotusnote`, `ipx`, `entrust-svc-hand`, `citriximaclient`, `rtc-pm-port`, `ftp`, `aol`, `xdmcp`, `oraclenames`, `login`, `iscsi`, `ttc`, `imaps`, `socks`, `ssh`, `dnsix`, `daytime`, `sip`, `discard`, `ntp`, `ldaps`, `https`, `vdolive`, `ica`, `net8-cman`, `cuseeme`, `netstat`, `sms`, `streamworks`, `rtelnet`, `who`, `kazaa`, `ssp`, `dbase`, `timed`, `cddbp`, `telnets`, `ymsgr`, `ident`, `bgp`, `ddns-v3`, `vqp`, `irc`, `ipass`, `x11`, `dns`, `lotusmtap`, `mysql`, `nfs`, `msnmsgr`, `netshow`, `sqlserv`, `hp-managed-node`, `ncp`, `shell`, `realmedia`, `msrpc`, `clp` ## Import diff --git a/docs/resources/policy_object_unified_advanced_inspection_profile.md b/docs/resources/policy_object_unified_advanced_inspection_profile.md index bc0e803f..c1283910 100644 --- a/docs/resources/policy_object_unified_advanced_inspection_profile.md +++ b/docs/resources/policy_object_unified_advanced_inspection_profile.md @@ -32,17 +32,17 @@ resource "sdwan_policy_object_unified_advanced_inspection_profile" "example" { ### Required -- `advanced_malware_protection_list_id` (String) - `feature_profile_id` (String) Feature Profile ID -- `intrusion_prevention_list_id` (String) - `name` (String) The name of the Policy_object - `tls_decryption_action` (String) - Choices: `decrypt`, `neverDecrypt`, `skipDecrypt` -- `tls_ssl_profile_list_id` (String) -- `url_filtering_list_id` (String) ### Optional +- `advanced_malware_protection_list_id` (String) - `description` (String) The description of the Policy_object +- `intrusion_prevention_list_id` (String) +- `tls_ssl_profile_list_id` (String) +- `url_filtering_list_id` (String) ### Read-Only diff --git a/docs/resources/policy_object_unified_advanced_malware_protection.md b/docs/resources/policy_object_unified_advanced_malware_protection.md index 9fbbcaa0..c9f8eaa3 100644 --- a/docs/resources/policy_object_unified_advanced_malware_protection.md +++ b/docs/resources/policy_object_unified_advanced_malware_protection.md @@ -19,7 +19,6 @@ resource "sdwan_policy_object_unified_advanced_malware_protection" "example" { name = "Example" description = "My Example" feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" - match_all_vpn = true amp_cloud_region = "nam" amp_cloud_region_est_server = "nam" alert_log_level = "critical" @@ -40,15 +39,16 @@ resource "sdwan_policy_object_unified_advanced_malware_protection" "example" { - `amp_cloud_region_est_server` (String) - Choices: `nam`, `eur`, `apjc` - `feature_profile_id` (String) Feature Profile ID - `file_analysis` (Boolean) -- `file_analysis_alert_log_level` (String) - Choices: `critical`, `warning`, `info` -- `file_analysis_cloud_region` (String) - Choices: `nam`, `eur` -- `file_analysis_file_types` (Set of String) -- `match_all_vpn` (Boolean) - `name` (String) The name of the Policy_object ### Optional - `description` (String) The description of the Policy_object +- `file_analysis_alert_log_level` (String) , Attribute conditional on `file_analysis` being equal to `true` + - Choices: `critical`, `warning`, `info` +- `file_analysis_cloud_region` (String) , Attribute conditional on `file_analysis` being equal to `true` + - Choices: `nam`, `eur` +- `file_analysis_file_types` (Set of String) , Attribute conditional on `file_analysis` being equal to `true` ### Read-Only diff --git a/docs/resources/policy_object_unified_intrusion_prevention.md b/docs/resources/policy_object_unified_intrusion_prevention.md index 3ce12093..0e3df5e4 100644 --- a/docs/resources/policy_object_unified_intrusion_prevention.md +++ b/docs/resources/policy_object_unified_intrusion_prevention.md @@ -16,14 +16,14 @@ This resource can manage a Policy Object Unified Intrusion Prevention Policy_obj ```terraform resource "sdwan_policy_object_unified_intrusion_prevention" "example" { - name = "Example" - description = "My Example" - feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" - signature_set = "balanced" - inspection_mode = "detection" - ips_signature_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" - log_level = "error" - custom_signature = false + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + signature_set = "balanced" + inspection_mode = "detection" + ips_signature_allow_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + log_level = "error" + custom_signature = false } ``` @@ -32,11 +32,9 @@ resource "sdwan_policy_object_unified_intrusion_prevention" "example" { ### Required -- `custom_signature` (Boolean) Can be one of the enum value - `feature_profile_id` (String) Feature Profile ID - `inspection_mode` (String) Can be one of the enum value - Choices: `detection`, `protection` -- `ips_signature_list_id` (String) - `log_level` (String) Can be one of the enum value - Choices: `emergency`, `alert`, `critical`, `error`, `warning`, `notice`, `info`, `debug` - `name` (String) The name of the Policy_object @@ -45,7 +43,9 @@ resource "sdwan_policy_object_unified_intrusion_prevention" "example" { ### Optional +- `custom_signature` (Boolean) Can be one of the enum value - `description` (String) The description of the Policy_object +- `ips_signature_allow_list_id` (String) ### Read-Only diff --git a/docs/resources/policy_object_unified_tls_ssl_decryption.md b/docs/resources/policy_object_unified_tls_ssl_decryption.md index e298d7e4..35a2c01d 100644 --- a/docs/resources/policy_object_unified_tls_ssl_decryption.md +++ b/docs/resources/policy_object_unified_tls_ssl_decryption.md @@ -19,12 +19,11 @@ resource "sdwan_policy_object_unified_tls_ssl_decryption" "example" { name = "Example" description = "My Example" feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" - enable_ssl = true expired_certificate = "drop" untrusted_certificate = "drop" certificate_revocation_status = "ocsp" unknown_revocation_status = "decrypt" - unsupported_protocol_versions = "no-decrypt" + unsupported_protocol_versions = "drop" unsupported_cipher_suites = "drop" failure_mode = "close" default_ca_certificate_bundle = true @@ -44,15 +43,12 @@ resource "sdwan_policy_object_unified_tls_ssl_decryption" "example" { - `certificate_revocation_status` (String) If value is none unknown status not required, if value is ocsp then unknown status is required - Choices: `ocsp`, `none` - `ec_key_type` (String) - Choices: `P256`, `P384`, `P521` -- `enable_ssl` (Boolean) If false, no other fields should be provided, if true all fields should be provided - `expired_certificate` (String) - Choices: `decrypt`, `drop` - `failure_mode` (String) - Choices: `close`, `open` - `feature_profile_id` (String) Feature Profile ID - `minimal_tls_ver` (String) - Choices: `TLSv1`, `TLSv1.1`, `TLSv1.2` - `name` (String) The name of the Policy_object - `rsa_keypair_modules` (String) - Choices: `1024`, `2048`, `4096` -- `unknown_revocation_status` (String) Only required if certificateRevocationStatus is oscp, if value is none then field shouldn't be here - - Choices: `decrypt`, `drop` - `unsupported_cipher_suites` (String) - Choices: `no-decrypt`, `drop` - `unsupported_protocol_versions` (String) - Choices: `no-decrypt`, `drop` - `untrusted_certificate` (String) - Choices: `decrypt`, `drop` @@ -63,6 +59,8 @@ resource "sdwan_policy_object_unified_tls_ssl_decryption" "example" { - `default_ca_certificate_bundle` (Boolean) - `description` (String) The description of the Policy_object - `file_name` (String) +- `unknown_revocation_status` (String) Only required if certificateRevocationStatus is oscp, if value is none then field shouldn't be here, Attribute conditional on `certificate_revocation_status` being equal to `ocsp` + - Choices: `decrypt`, `drop` ### Read-Only diff --git a/docs/resources/policy_object_unified_tls_ssl_profile.md b/docs/resources/policy_object_unified_tls_ssl_profile.md index da157cfc..a5d8ede0 100644 --- a/docs/resources/policy_object_unified_tls_ssl_profile.md +++ b/docs/resources/policy_object_unified_tls_ssl_profile.md @@ -37,20 +37,22 @@ resource "sdwan_policy_object_unified_tls_ssl_profile" "example" { ### Required - `decrypt_categories` (Set of String) -- `decrypt_threshold` (String) - Choices: `high-risk`, `low-risk`, `moderate-risk`, `suspicious`, `trustworthy` - `fail_decrypt` (Boolean) - `feature_profile_id` (String) Feature Profile ID - `name` (String) The name of the Policy_object - `no_decrypt_categories` (Set of String) - `pass_through_categories` (Set of String) - `reputation` (Boolean) -- `threshold_categories` (String) - Choices: `high-risk`, `low-risk`, `moderate-risk`, `suspicious`, `trustworthy` -- `url_allow_list_id` (String) -- `url_block_list_id` (String) ### Optional +- `decrypt_threshold` (String) , Attribute conditional on `reputation` being equal to `true` + - Choices: `high-risk`, `low-risk`, `moderate-risk`, `suspicious`, `trustworthy` - `description` (String) The description of the Policy_object +- `threshold_categories` (String) , Attribute conditional on `reputation` being equal to `true` + - Choices: `high-risk`, `low-risk`, `moderate-risk`, `suspicious`, `trustworthy` +- `url_allow_list_id` (String) +- `url_block_list_id` (String) ### Read-Only diff --git a/docs/resources/policy_object_unified_url_filtering.md b/docs/resources/policy_object_unified_url_filtering.md index 40d5587e..a2b545ba 100644 --- a/docs/resources/policy_object_unified_url_filtering.md +++ b/docs/resources/policy_object_unified_url_filtering.md @@ -26,7 +26,6 @@ resource "sdwan_policy_object_unified_url_filtering" "example" { url_block_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" block_page_action = "text" block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator" - redirect_url = "www.example.com" enable_alerts = true alerts = ["blacklist"] } @@ -37,22 +36,22 @@ resource "sdwan_policy_object_unified_url_filtering" "example" { ### Required -- `alerts` (Set of String) - `block_page_action` (String) - Choices: `text`, `redirect-url` -- `block_page_contents` (String) - `enable_alerts` (Boolean) - `feature_profile_id` (String) Feature Profile ID - `name` (String) The name of the Policy_object -- `redirect_url` (String) -- `url_allow_list_id` (String) -- `url_block_list_id` (String) - `web_categories` (Set of String) - `web_categories_action` (String) - Choices: `block`, `allow` - `web_reputation` (String) - Choices: `high-risk`, `low-risk`, `moderate-risk`, `suspicious`, `trustworthy` ### Optional +- `alerts` (Set of String) , Attribute conditional on `enable_alerts` being equal to `true` +- `block_page_contents` (String) , Attribute conditional on `block_page_action` being equal to `text` - `description` (String) The description of the Policy_object +- `redirect_url` (String) , Attribute conditional on `block_page_action` being equal to `redirect-url` +- `url_allow_list_id` (String) +- `url_block_list_id` (String) ### Read-Only diff --git a/examples/resources/sdwan_policy_object_security_protocol_list/resource.tf b/examples/resources/sdwan_policy_object_security_protocol_list/resource.tf index d19b8042..5d6a8ef1 100644 --- a/examples/resources/sdwan_policy_object_security_protocol_list/resource.tf +++ b/examples/resources/sdwan_policy_object_security_protocol_list/resource.tf @@ -4,7 +4,7 @@ resource "sdwan_policy_object_security_protocol_list" "example" { feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" entries = [ { - protocol_names = "aol" + protocol_name = "aol" } ] } diff --git a/examples/resources/sdwan_policy_object_unified_advanced_malware_protection/resource.tf b/examples/resources/sdwan_policy_object_unified_advanced_malware_protection/resource.tf index f52ef471..2e018f02 100644 --- a/examples/resources/sdwan_policy_object_unified_advanced_malware_protection/resource.tf +++ b/examples/resources/sdwan_policy_object_unified_advanced_malware_protection/resource.tf @@ -2,7 +2,6 @@ resource "sdwan_policy_object_unified_advanced_malware_protection" "example" { name = "Example" description = "My Example" feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" - match_all_vpn = true amp_cloud_region = "nam" amp_cloud_region_est_server = "nam" alert_log_level = "critical" diff --git a/examples/resources/sdwan_policy_object_unified_intrusion_prevention/resource.tf b/examples/resources/sdwan_policy_object_unified_intrusion_prevention/resource.tf index 4c344961..18d4cb38 100644 --- a/examples/resources/sdwan_policy_object_unified_intrusion_prevention/resource.tf +++ b/examples/resources/sdwan_policy_object_unified_intrusion_prevention/resource.tf @@ -1,10 +1,10 @@ resource "sdwan_policy_object_unified_intrusion_prevention" "example" { - name = "Example" - description = "My Example" - feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" - signature_set = "balanced" - inspection_mode = "detection" - ips_signature_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" - log_level = "error" - custom_signature = false + name = "Example" + description = "My Example" + feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" + signature_set = "balanced" + inspection_mode = "detection" + ips_signature_allow_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" + log_level = "error" + custom_signature = false } diff --git a/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf b/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf index 23a90771..86e48f19 100644 --- a/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf +++ b/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf @@ -2,12 +2,11 @@ resource "sdwan_policy_object_unified_tls_ssl_decryption" "example" { name = "Example" description = "My Example" feature_profile_id = "f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac" - enable_ssl = true expired_certificate = "drop" untrusted_certificate = "drop" certificate_revocation_status = "ocsp" unknown_revocation_status = "decrypt" - unsupported_protocol_versions = "no-decrypt" + unsupported_protocol_versions = "drop" unsupported_cipher_suites = "drop" failure_mode = "close" default_ca_certificate_bundle = true diff --git a/examples/resources/sdwan_policy_object_unified_url_filtering/resource.tf b/examples/resources/sdwan_policy_object_unified_url_filtering/resource.tf index 553a6a0e..c38f09cf 100644 --- a/examples/resources/sdwan_policy_object_unified_url_filtering/resource.tf +++ b/examples/resources/sdwan_policy_object_unified_url_filtering/resource.tf @@ -9,7 +9,6 @@ resource "sdwan_policy_object_unified_url_filtering" "example" { url_block_list_id = "2ad58d78-59ee-46d3-86dd-7b6b7ca09f38" block_page_action = "text" block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator" - redirect_url = "www.example.com" enable_alerts = true alerts = ["blacklist"] } diff --git a/gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml b/gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml index 023636c4..77ae9978 100644 --- a/gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml +++ b/gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml @@ -17,7 +17,7 @@ attributes: mandatory: true attributes: - model_name: protocolName - tf_name: protocol_names + tf_name: protocol_name id: true mandatory: true example: aol diff --git a/gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml b/gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml index b8065cf9..6af9a37f 100644 --- a/gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml +++ b/gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml @@ -18,21 +18,25 @@ attributes: - model_name: refId tf_name: intrusion_prevention_list_id data_path: [intrusionPrevention] + ignore_mandatory: true example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 test_value: sdwan_policy_object_unified_intrusion_prevention.test.id - model_name: refId tf_name: url_filtering_list_id data_path: [urlFiltering] + ignore_mandatory: true example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 test_value: sdwan_policy_object_security_url_allow_list.test.id - model_name: refId tf_name: advanced_malware_protection_list_id data_path: [advancedMalwareProtection] + ignore_mandatory: true example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 test_value: sdwan_policy_object_unified_advanced_malware_protection.test.id - model_name: refId tf_name: tls_ssl_profile_list_id data_path: [sslDecryptionProfile] + ignore_mandatory: true example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 test_value: sdwan_policy_object_unified_tls_ssl_profile.test.id @@ -107,7 +111,6 @@ test_prerequisites: | name = "TF_TEST_ADVANCED_MALWARE" description = "My Example" feature_profile_id = sdwan_policy_object_feature_profile.test.id - match_all_vpn = true amp_cloud_region = "nam" amp_cloud_region_est_server = "nam" alert_log_level = "critical" diff --git a/gen/definitions/profile_parcels/policy_object_unified_advanced_malware_protection.yaml b/gen/definitions/profile_parcels/policy_object_unified_advanced_malware_protection.yaml index 99b17f3f..66014b18 100644 --- a/gen/definitions/profile_parcels/policy_object_unified_advanced_malware_protection.yaml +++ b/gen/definitions/profile_parcels/policy_object_unified_advanced_malware_protection.yaml @@ -15,27 +15,48 @@ attributes: test_value: sdwan_policy_object_feature_profile.test.id - model_name: matchAllVpn tf_name: match_all_vpn + value: true + value_type: "global" example: true - model_name: fileReputationCloudServer tf_name: amp_cloud_region + mandatory: true example: nam - model_name: fileReputationEstServer tf_name: amp_cloud_region_est_server + mandatory: true example: nam - model_name: fileReputationAlert tf_name: alert_log_level + mandatory: true example: critical - model_name: fileAnalysisEnabled tf_name: file_analysis + mandatory: true example: true - model_name: fileAnalysisCloudServer tf_name: file_analysis_cloud_region + ignore_mandatory: true + conditional_attribute: + name: file_analysis + value: true + type: Bool example: nam - model_name: fileAnalysisFileTypes tf_name: file_analysis_file_types + ignore_mandatory: true + conditional_attribute: + name: file_analysis + value: true + type: Bool example: pdf - model_name: fileAnalysisAlert tf_name: file_analysis_alert_log_level + ignore_mandatory: true + conditional_attribute: + name: file_analysis + value: true + type: Bool example: critical test_prerequisites: | diff --git a/gen/definitions/profile_parcels/policy_object_unified_intrusion_prevention.yaml b/gen/definitions/profile_parcels/policy_object_unified_intrusion_prevention.yaml index 0654a333..57d4f098 100644 --- a/gen/definitions/profile_parcels/policy_object_unified_intrusion_prevention.yaml +++ b/gen/definitions/profile_parcels/policy_object_unified_intrusion_prevention.yaml @@ -18,13 +18,15 @@ attributes: - model_name: inspectionMode example: detection - model_name: refId - tf_name: ips_signature_list_id + tf_name: ips_signature_allow_list_id data_path: [signatureAllowedList] + ignore_mandatory: true example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 test_value: sdwan_policy_object_security_ips_signature.test.id - model_name: logLevel example: error - model_name: customSignature + ignore_mandatory: true example: false test_prerequisites: | diff --git a/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml b/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml index bbe1e470..4801eaad 100644 --- a/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml +++ b/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml @@ -15,18 +15,28 @@ attributes: test_value: sdwan_policy_object_feature_profile.test.id - model_name: sslEnable tf_name: enable_ssl + value: true + value_type: "global" example: true + - model_name: expiredCertificate example: drop - model_name: untrustedCertificate example: drop + - model_name: certificateRevocationStatus example: ocsp - model_name: unknownStatus tf_name: unknown_revocation_status + ignore_mandatory: true + conditional_attribute: + name: certificate_revocation_status + value: ocsp example: decrypt + + - model_name: unsupportedProtocolVersions - example: no-decrypt + example: drop - model_name: unsupportedCipherSuites example: drop - model_name: failureMode @@ -35,25 +45,32 @@ attributes: tf_name: default_ca_certificate_bundle data_path: [caCertBundle] example: true + - model_name: fileName data_path: [caCertBundle] + ignore_mandatory: true exclude_test: true example: dummy.pem - model_name: bundleString data_path: [caCertBundle] + ignore_mandatory: true exclude_test: true example: testString + - model_name: keyModulus tf_name: rsa_keypair_modules example: 2048 + - model_name: eckeyType tf_name: ec_key_type example: P384 - model_name: certificateLifetime example: 1 + - model_name: minTlsVer tf_name: minimal_tls_ver example: TLSv1.2 + - model_name: caTpLabel value: PROXY-SIGNING-CA diff --git a/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_profile.yaml b/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_profile.yaml index 33b43120..cb942448 100644 --- a/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_profile.yaml +++ b/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_profile.yaml @@ -24,20 +24,32 @@ attributes: - model_name: reputation example: true - model_name: decryptThreshold + ignore_mandatory: true + conditional_attribute: + name: reputation + value: true + type: Bool example: moderate-risk - model_name: skipDecryptThreshold tf_name: threshold_categories + ignore_mandatory: true + conditional_attribute: + name: reputation + value: true + type: Bool example: moderate-risk - model_name: failDecrypt example: true - model_name: refId tf_name: url_allow_list_id data_path: [urlAllowedList] + ignore_mandatory: true example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 test_value: sdwan_policy_object_security_url_allow_list.test.id - model_name: refId tf_name: url_block_list_id data_path: [urlBlockedList] + ignore_mandatory: true example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 test_value: sdwan_policy_object_security_url_block_list.test.id diff --git a/gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml b/gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml index 95325943..f3c05f37 100644 --- a/gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml +++ b/gen/definitions/profile_parcels/policy_object_unified_url_filtering.yaml @@ -14,30 +14,51 @@ attributes: example: f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac test_value: sdwan_policy_object_feature_profile.test.id - model_name: webCategoriesAction + mandatory: true example: block - model_name: webCategories + mandatory: true example: confirmed-spam-sources - model_name: webReputation + mandatory: true example: suspicious - model_name: refId tf_name: url_allow_list_id data_path: [urlAllowedList] + ignore_mandatory: true example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 test_value: sdwan_policy_object_security_url_allow_list.test.id - model_name: refId tf_name: url_block_list_id data_path: [urlBlockedList] + ignore_mandatory: true example: 2ad58d78-59ee-46d3-86dd-7b6b7ca09f38 test_value: sdwan_policy_object_security_url_block_list.test.id - model_name: blockPageAction example: text - model_name: blockPageContents + ignore_mandatory: true + conditional_attribute: + name: block_page_action + value: text example: Access to the requested page has been denied. Please contact your Network Administrator - model_name: redirectUrl + ignore_mandatory: true + conditional_attribute: + name: block_page_action + value: redirect-url + exclude_test: true example: www.example.com - model_name: enableAlerts example: true - model_name: alerts + ignore_mandatory: true + conditional_attribute: + name: enable_alerts + value: true + type: Bool + enum_values: ["blacklist", "whitelist", "categories-reputation"] + ignore_enum: true example: blacklist test_prerequisites: | diff --git a/gen/generator.go b/gen/generator.go index e6e56108..08d779a9 100644 --- a/gen/generator.go +++ b/gen/generator.go @@ -231,6 +231,7 @@ type YamlConfigAttribute struct { Reference bool `yaml:"reference"` Variable bool `yaml:"variable"` Mandatory bool `yaml:"mandatory"` + IgnoreMandatory bool `yaml:"ignore_mandatory"` Optional bool `yaml:"optional"` WriteOnly bool `yaml:"write_only"` TfOnly bool `yaml:"tf_only"` @@ -256,6 +257,7 @@ type YamlConfigAttribute struct { DefaultValuePresent bool `yaml:"default_value_present"` DefaultValueEmptyString bool `yaml:"default_value_empty_string"` Value string `yaml:"value"` + ValueType string `yaml:"value_type"` TestValue string `yaml:"test_value"` SecondaryTestValue string `yaml:"secondary_test_value"` MinimumTestValue string `yaml:"minimum_test_value"` @@ -863,6 +865,7 @@ func parseProfileParcelAttribute(attr *YamlConfigAttribute, model gjson.Result, } else { if noGlobal { attr.Value = value.String() + attr.ValueType = "default" } else { attr.DefaultValue = value.String() } @@ -873,6 +876,7 @@ func parseProfileParcelAttribute(attr *YamlConfigAttribute, model gjson.Result, } else { if noGlobal { attr.Value = value.String() + attr.ValueType = "default" } else { attr.DefaultValue = value.String() } @@ -880,6 +884,7 @@ func parseProfileParcelAttribute(attr *YamlConfigAttribute, model gjson.Result, } else if value := d.Get("properties.value.minimum"); value.Exists() { if noGlobal { attr.Value = value.String() + attr.ValueType = "default" } else { attr.DefaultValue = value.String() } @@ -887,7 +892,7 @@ func parseProfileParcelAttribute(attr *YamlConfigAttribute, model gjson.Result, } else if isOneOfAttribute { attr.ExcludeNull = true } else { - if !attr.Variable { + if !attr.Variable && !attr.IgnoreMandatory { attr.Mandatory = true } } diff --git a/gen/schema/schema.yaml b/gen/schema/schema.yaml index 7b7f9be9..b8d03388 100644 --- a/gen/schema/schema.yaml +++ b/gen/schema/schema.yaml @@ -44,6 +44,7 @@ attribute: reference: bool(required=False) # Indicates that the attribute is being used in the url path variable: bool(required=False) # Indicates that this attribute can be provided as a feature template or profile parcel variable mandatory: bool(required=False) # Set to true if the attribute is mandatory + ignore_mandatory: bool(required=False) # Set to true if schema mandatory value should be ignored optional: bool(required=False) # Set to true if the attribute is optional write_only: bool(required=False) # Set to true if the attribute is write-only, meaning we cannot read the value tf_only: bool(required=False) # Set to true if this attribute is only used in Terraform but not added to payload @@ -69,6 +70,7 @@ attribute: default_value_present: bool(required=False) # Set to true if profile parcel has default value in schema default_value_empty_string: bool(required=False) # Set to true if default value should be an empty string value: any(str(), int(), bool(), required=False) # Hardcoded value for the attribute + value_type: str(required=False) # Hardcoded value for the attribute test_value: str(required=False) # Value used for acceptance test secondary_test_value: str(required=False) # Value used for acceptance test minimum_test_value: any(str(), int(), bool(), num(), required=False) # Value used for "minimum" resource acceptance test diff --git a/gen/templates/profile_parcels/model.go b/gen/templates/profile_parcels/model.go index 146d4019..6cbda242 100644 --- a/gen/templates/profile_parcels/model.go +++ b/gen/templates/profile_parcels/model.go @@ -165,7 +165,7 @@ func (data {{camelCase .Name}}) toBody(ctx context.Context) string { {{- range .Attributes}} {{- if .Value}} if true{{if ne .ConditionalAttribute.Name ""}} {{if eq .ConditionalAttribute.Type "Bool"}} && data.{{toGoName .ConditionalAttribute.Name}}.ValueBool() == {{.ConditionalAttribute.Value}} {{else}} && data.{{toGoName .ConditionalAttribute.Name}}.ValueString() == "{{.ConditionalAttribute.Value}}" {{end}}{{end}} { - body, _ = sjson.Set(body, path+"{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.optionType", "default") + body, _ = sjson.Set(body, path+"{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.optionType", {{if .ValueType}}"{{.ValueType}}"{{else}}"default"{{end}}) body, _ = sjson.Set(body, path+"{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.value", {{if eq .Type "String"}}"{{end}}{{.Value}}{{if eq .Type "String"}}"{{end}}) } {{- else if and (or (eq .Type "String") (eq .Type "Int64") (eq .Type "Float64") (eq .Type "Bool") (isListSet .)) (not .Reference)}} @@ -202,7 +202,7 @@ func (data {{camelCase .Name}}) toBody(ctx context.Context) string { {{- range .Attributes}} {{- if .Value}} if true{{if ne .ConditionalAttribute.Name ""}} {{if eq .ConditionalAttribute.Type "Bool"}} && item.{{toGoName .ConditionalAttribute.Name}}.ValueBool() == {{.ConditionalAttribute.Value}} {{else}} && item.{{toGoName .ConditionalAttribute.Name}}.ValueString() == "{{.ConditionalAttribute.Value}}" {{end}}{{end}} { - itemBody, _ = sjson.Set(itemBody, "{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.optionType", "default") + itemBody, _ = sjson.Set(itemBody, "{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.optionType", {{if .ValueType}}"{{.ValueType}}"{{else}}"default"{{end}}) itemBody, _ = sjson.Set(itemBody, "{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.value", {{if eq .Type "String"}}"{{end}}{{.Value}}{{if eq .Type "String"}}"{{end}}) } {{- else if or (eq .Type "String") (eq .Type "Int64") (eq .Type "Float64") (eq .Type "Bool") (isListSet .)}} @@ -239,7 +239,7 @@ func (data {{camelCase .Name}}) toBody(ctx context.Context) string { {{- range .Attributes}} {{- if .Value}} if true{{if ne .ConditionalAttribute.Name ""}} {{if eq .ConditionalAttribute.Type "Bool"}} && childItem.{{toGoName .ConditionalAttribute.Name}}.ValueBool() == {{.ConditionalAttribute.Value}} {{else}} && childItem.{{toGoName .ConditionalAttribute.Name}}.ValueString() == "{{.ConditionalAttribute.Value}}" {{end}}{{end}} { - itemChildBody, _ = sjson.Set(itemChildBody, "{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.optionType", "default") + itemChildBody, _ = sjson.Set(itemChildBody, "{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.optionType", {{if .ValueType}}"{{.ValueType}}"{{else}}"default"{{end}}) itemChildBody, _ = sjson.Set(itemChildBody, "{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.value", {{if eq .Type "String"}}"{{end}}{{.Value}}{{if eq .Type "String"}}"{{end}}) } {{- else if or (eq .Type "String") (eq .Type "Int64") (eq .Type "Float64") (eq .Type "Bool") (isListSet .)}} @@ -276,7 +276,7 @@ func (data {{camelCase .Name}}) toBody(ctx context.Context) string { {{- range .Attributes}} {{- if .Value}} if true{{if ne .ConditionalAttribute.Name ""}} {{if eq .ConditionalAttribute.Type "Bool"}} && childChildItem.{{toGoName .ConditionalAttribute.Name}}.ValueBool() == {{.ConditionalAttribute.Value}} {{else}} && childChildItem.{{toGoName .ConditionalAttribute.Name}}.ValueString() == "{{.ConditionalAttribute.Value}}" {{end}}{{end}} { - itemChildChildBody, _ = sjson.Set(itemChildChildBody, "{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.optionType", "default") + itemChildChildBody, _ = sjson.Set(itemChildChildBody, "{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.optionType", {{if .ValueType}}"{{.ValueType}}"{{else}}"default"{{end}}) itemChildChildBody, _ = sjson.Set(itemChildChildBody, "{{range .DataPath}}{{.}}.{{end}}{{.ModelName}}.value", {{if eq .Type "String"}}"{{end}}{{.Value}}{{if eq .Type "String"}}"{{end}}) } {{- else if or (eq .Type "String") (eq .Type "Int64") (eq .Type "Float64") (eq .Type "Bool") (isListSet .)}} diff --git a/internal/provider/data_source_sdwan_policy_object_security_protocol_list.go b/internal/provider/data_source_sdwan_policy_object_security_protocol_list.go index 9c9cf9a8..9e3d0069 100644 --- a/internal/provider/data_source_sdwan_policy_object_security_protocol_list.go +++ b/internal/provider/data_source_sdwan_policy_object_security_protocol_list.go @@ -82,7 +82,7 @@ func (d *PolicyObjectSecurityProtocolListProfileParcelDataSource) Schema(ctx con Computed: true, NestedObject: schema.NestedAttributeObject{ Attributes: map[string]schema.Attribute{ - "protocol_names": schema.StringAttribute{ + "protocol_name": schema.StringAttribute{ MarkdownDescription: "", Computed: true, }, diff --git a/internal/provider/data_source_sdwan_policy_object_security_protocol_list_test.go b/internal/provider/data_source_sdwan_policy_object_security_protocol_list_test.go index 63318c0a..6d790819 100644 --- a/internal/provider/data_source_sdwan_policy_object_security_protocol_list_test.go +++ b/internal/provider/data_source_sdwan_policy_object_security_protocol_list_test.go @@ -33,7 +33,7 @@ func TestAccDataSourceSdwanPolicyObjectSecurityProtocolListProfileParcel(t *test t.Skip("skipping test, set environment variable SDWAN_2012") } var checks []resource.TestCheckFunc - checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_security_protocol_list.test", "entries.0.protocol_names", "aol")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_security_protocol_list.test", "entries.0.protocol_name", "aol")) resource.Test(t, resource.TestCase{ PreCheck: func() { testAccPreCheck(t) }, ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, @@ -65,7 +65,7 @@ func testAccDataSourceSdwanPolicyObjectSecurityProtocolListProfileParcelConfig() config += ` description = "Terraform integration test"` + "\n" config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" config += ` entries = [{` + "\n" - config += ` protocol_names = "aol"` + "\n" + config += ` protocol_name = "aol"` + "\n" config += ` }]` + "\n" config += `}` + "\n" diff --git a/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go b/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go index 559fcaea..5d26b518 100644 --- a/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go +++ b/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go @@ -120,7 +120,6 @@ resource "sdwan_policy_object_unified_advanced_malware_protection" "test" { name = "TF_TEST_ADVANCED_MALWARE" description = "My Example" feature_profile_id = sdwan_policy_object_feature_profile.test.id - match_all_vpn = true amp_cloud_region = "nam" amp_cloud_region_est_server = "nam" alert_log_level = "critical" diff --git a/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection.go b/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection.go index bdac27de..c578487d 100644 --- a/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection.go +++ b/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection.go @@ -78,10 +78,6 @@ func (d *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelDataSource) Sc MarkdownDescription: "Feature Profile ID", Required: true, }, - "match_all_vpn": schema.BoolAttribute{ - MarkdownDescription: "", - Computed: true, - }, "amp_cloud_region": schema.StringAttribute{ MarkdownDescription: "", Computed: true, diff --git a/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection_test.go b/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection_test.go index 430083a8..5f7c783e 100644 --- a/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection_test.go +++ b/internal/provider/data_source_sdwan_policy_object_unified_advanced_malware_protection_test.go @@ -33,7 +33,6 @@ func TestAccDataSourceSdwanPolicyObjectUnifiedAdvancedMalwareProtectionProfilePa t.Skip("skipping test, set environment variable SDWAN_2012") } var checks []resource.TestCheckFunc - checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_malware_protection.test", "match_all_vpn", "true")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_malware_protection.test", "amp_cloud_region", "nam")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_malware_protection.test", "amp_cloud_region_est_server", "nam")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_advanced_malware_protection.test", "alert_log_level", "critical")) @@ -71,7 +70,6 @@ func testAccDataSourceSdwanPolicyObjectUnifiedAdvancedMalwareProtectionProfilePa config += ` name = "TF_TEST"` + "\n" config += ` description = "Terraform integration test"` + "\n" config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" - config += ` match_all_vpn = true` + "\n" config += ` amp_cloud_region = "nam"` + "\n" config += ` amp_cloud_region_est_server = "nam"` + "\n" config += ` alert_log_level = "critical"` + "\n" diff --git a/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention.go b/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention.go index 87ef4d45..6327ed41 100644 --- a/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention.go +++ b/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention.go @@ -85,7 +85,7 @@ func (d *PolicyObjectUnifiedIntrusionPreventionProfileParcelDataSource) Schema(c MarkdownDescription: "Can be one of the enum value", Computed: true, }, - "ips_signature_list_id": schema.StringAttribute{ + "ips_signature_allow_list_id": schema.StringAttribute{ MarkdownDescription: "", Computed: true, }, diff --git a/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention_test.go b/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention_test.go index 6da50085..2ceae697 100644 --- a/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention_test.go +++ b/internal/provider/data_source_sdwan_policy_object_unified_intrusion_prevention_test.go @@ -82,7 +82,7 @@ func testAccDataSourceSdwanPolicyObjectUnifiedIntrusionPreventionProfileParcelCo config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" config += ` signature_set = "balanced"` + "\n" config += ` inspection_mode = "detection"` + "\n" - config += ` ips_signature_list_id = sdwan_policy_object_security_ips_signature.test.id` + "\n" + config += ` ips_signature_allow_list_id = sdwan_policy_object_security_ips_signature.test.id` + "\n" config += ` log_level = "error"` + "\n" config += ` custom_signature = false` + "\n" config += `}` + "\n" diff --git a/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption.go b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption.go index 9832cb63..59a4fc86 100644 --- a/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption.go +++ b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption.go @@ -77,10 +77,6 @@ func (d *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelDataSource) Schema(ctx MarkdownDescription: "Feature Profile ID", Required: true, }, - "enable_ssl": schema.BoolAttribute{ - MarkdownDescription: "If false, no other fields should be provided, if true all fields should be provided", - Computed: true, - }, "expired_certificate": schema.StringAttribute{ MarkdownDescription: "", Computed: true, diff --git a/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go index a42c26d9..4df6545f 100644 --- a/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go +++ b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go @@ -33,12 +33,11 @@ func TestAccDataSourceSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcel(t *t t.Skip("skipping test, set environment variable SDWAN_2012") } var checks []resource.TestCheckFunc - checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "enable_ssl", "true")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "expired_certificate", "drop")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "untrusted_certificate", "drop")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "certificate_revocation_status", "ocsp")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "unknown_revocation_status", "decrypt")) - checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_protocol_versions", "no-decrypt")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_protocol_versions", "drop")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_cipher_suites", "drop")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "failure_mode", "close")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "default_ca_certificate_bundle", "true")) @@ -76,12 +75,11 @@ func testAccDataSourceSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcelConfi config += ` name = "TF_TEST"` + "\n" config += ` description = "Terraform integration test"` + "\n" config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" - config += ` enable_ssl = true` + "\n" config += ` expired_certificate = "drop"` + "\n" config += ` untrusted_certificate = "drop"` + "\n" config += ` certificate_revocation_status = "ocsp"` + "\n" config += ` unknown_revocation_status = "decrypt"` + "\n" - config += ` unsupported_protocol_versions = "no-decrypt"` + "\n" + config += ` unsupported_protocol_versions = "drop"` + "\n" config += ` unsupported_cipher_suites = "drop"` + "\n" config += ` failure_mode = "close"` + "\n" config += ` default_ca_certificate_bundle = true` + "\n" diff --git a/internal/provider/data_source_sdwan_policy_object_unified_url_filtering_test.go b/internal/provider/data_source_sdwan_policy_object_unified_url_filtering_test.go index 4ea0ddae..098b6e30 100644 --- a/internal/provider/data_source_sdwan_policy_object_unified_url_filtering_test.go +++ b/internal/provider/data_source_sdwan_policy_object_unified_url_filtering_test.go @@ -37,7 +37,6 @@ func TestAccDataSourceSdwanPolicyObjectUnifiedURLFilteringProfileParcel(t *testi checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_url_filtering.test", "web_reputation", "suspicious")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_url_filtering.test", "block_page_action", "text")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_url_filtering.test", "block_page_contents", "Access to the requested page has been denied. Please contact your Network Administrator")) - checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_url_filtering.test", "redirect_url", "www.example.com")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_url_filtering.test", "enable_alerts", "true")) resource.Test(t, resource.TestCase{ PreCheck: func() { testAccPreCheck(t) }, @@ -98,7 +97,6 @@ func testAccDataSourceSdwanPolicyObjectUnifiedURLFilteringProfileParcelConfig() config += ` url_block_list_id = sdwan_policy_object_security_url_block_list.test.id` + "\n" config += ` block_page_action = "text"` + "\n" config += ` block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator"` + "\n" - config += ` redirect_url = "www.example.com"` + "\n" config += ` enable_alerts = true` + "\n" config += ` alerts = ["blacklist"]` + "\n" config += `}` + "\n" diff --git a/internal/provider/model_sdwan_policy_object_security_protocol_list.go b/internal/provider/model_sdwan_policy_object_security_protocol_list.go index faa1fb3c..51cc7fd0 100644 --- a/internal/provider/model_sdwan_policy_object_security_protocol_list.go +++ b/internal/provider/model_sdwan_policy_object_security_protocol_list.go @@ -41,7 +41,7 @@ type PolicyObjectSecurityProtocolList struct { } type PolicyObjectSecurityProtocolListEntries struct { - ProtocolNames types.String `tfsdk:"protocol_names"` + ProtocolName types.String `tfsdk:"protocol_name"` } // End of section. //template:end types @@ -70,10 +70,10 @@ func (data PolicyObjectSecurityProtocolList) toBody(ctx context.Context) string for _, item := range data.Entries { itemBody := "" - if !item.ProtocolNames.IsNull() { + if !item.ProtocolName.IsNull() { if true { itemBody, _ = sjson.Set(itemBody, "protocolName.optionType", "global") - itemBody, _ = sjson.Set(itemBody, "protocolName.value", item.ProtocolNames.ValueString()) + itemBody, _ = sjson.Set(itemBody, "protocolName.value", item.ProtocolName.ValueString()) } } body, _ = sjson.SetRaw(body, path+"entries.-1", itemBody) @@ -97,12 +97,12 @@ func (data *PolicyObjectSecurityProtocolList) fromBody(ctx context.Context, res data.Entries = make([]PolicyObjectSecurityProtocolListEntries, 0) value.ForEach(func(k, v gjson.Result) bool { item := PolicyObjectSecurityProtocolListEntries{} - item.ProtocolNames = types.StringNull() + item.ProtocolName = types.StringNull() if t := v.Get("protocolName.optionType"); t.Exists() { va := v.Get("protocolName.value") if t.String() == "global" { - item.ProtocolNames = types.StringValue(va.String()) + item.ProtocolName = types.StringValue(va.String()) } } data.Entries = append(data.Entries, item) @@ -124,7 +124,7 @@ func (data *PolicyObjectSecurityProtocolList) updateFromBody(ctx context.Context path := "payload.data." for i := range data.Entries { keys := [...]string{"protocolName"} - keyValues := [...]string{data.Entries[i].ProtocolNames.ValueString()} + keyValues := [...]string{data.Entries[i].ProtocolName.ValueString()} keyValuesVariables := [...]string{""} var r gjson.Result @@ -151,12 +151,12 @@ func (data *PolicyObjectSecurityProtocolList) updateFromBody(ctx context.Context return true }, ) - data.Entries[i].ProtocolNames = types.StringNull() + data.Entries[i].ProtocolName = types.StringNull() if t := r.Get("protocolName.optionType"); t.Exists() { va := r.Get("protocolName.value") if t.String() == "global" { - data.Entries[i].ProtocolNames = types.StringValue(va.String()) + data.Entries[i].ProtocolName = types.StringValue(va.String()) } } } diff --git a/internal/provider/model_sdwan_policy_object_unified_advanced_malware_protection.go b/internal/provider/model_sdwan_policy_object_unified_advanced_malware_protection.go index 3bc71a08..306fc680 100644 --- a/internal/provider/model_sdwan_policy_object_unified_advanced_malware_protection.go +++ b/internal/provider/model_sdwan_policy_object_unified_advanced_malware_protection.go @@ -38,7 +38,6 @@ type PolicyObjectUnifiedAdvancedMalwareProtection struct { Name types.String `tfsdk:"name"` Description types.String `tfsdk:"description"` FeatureProfileId types.String `tfsdk:"feature_profile_id"` - MatchAllVpn types.Bool `tfsdk:"match_all_vpn"` AmpCloudRegion types.String `tfsdk:"amp_cloud_region"` AmpCloudRegionEstServer types.String `tfsdk:"amp_cloud_region_est_server"` AlertLogLevel types.String `tfsdk:"alert_log_level"` @@ -70,11 +69,9 @@ func (data PolicyObjectUnifiedAdvancedMalwareProtection) toBody(ctx context.Cont body, _ = sjson.Set(body, "name", data.Name.ValueString()) body, _ = sjson.Set(body, "description", data.Description.ValueString()) path := "data." - if !data.MatchAllVpn.IsNull() { - if true { - body, _ = sjson.Set(body, path+"matchAllVpn.optionType", "global") - body, _ = sjson.Set(body, path+"matchAllVpn.value", data.MatchAllVpn.ValueBool()) - } + if true { + body, _ = sjson.Set(body, path+"matchAllVpn.optionType", "global") + body, _ = sjson.Set(body, path+"matchAllVpn.value", true) } if !data.AmpCloudRegion.IsNull() { if true { @@ -101,13 +98,13 @@ func (data PolicyObjectUnifiedAdvancedMalwareProtection) toBody(ctx context.Cont } } if !data.FileAnalysisCloudRegion.IsNull() { - if true { + if true && data.FileAnalysis.ValueBool() == true { body, _ = sjson.Set(body, path+"fileAnalysisCloudServer.optionType", "global") body, _ = sjson.Set(body, path+"fileAnalysisCloudServer.value", data.FileAnalysisCloudRegion.ValueString()) } } if !data.FileAnalysisFileTypes.IsNull() { - if true { + if true && data.FileAnalysis.ValueBool() == true { body, _ = sjson.Set(body, path+"fileAnalysisFileTypes.optionType", "global") var values []string data.FileAnalysisFileTypes.ElementsAs(ctx, &values, false) @@ -115,7 +112,7 @@ func (data PolicyObjectUnifiedAdvancedMalwareProtection) toBody(ctx context.Cont } } if !data.FileAnalysisAlertLogLevel.IsNull() { - if true { + if true && data.FileAnalysis.ValueBool() == true { body, _ = sjson.Set(body, path+"fileAnalysisAlert.optionType", "global") body, _ = sjson.Set(body, path+"fileAnalysisAlert.value", data.FileAnalysisAlertLogLevel.ValueString()) } @@ -134,14 +131,6 @@ func (data *PolicyObjectUnifiedAdvancedMalwareProtection) fromBody(ctx context.C data.Description = types.StringNull() } path := "payload.data." - data.MatchAllVpn = types.BoolNull() - - if t := res.Get(path + "matchAllVpn.optionType"); t.Exists() { - va := res.Get(path + "matchAllVpn.value") - if t.String() == "global" { - data.MatchAllVpn = types.BoolValue(va.Bool()) - } - } data.AmpCloudRegion = types.StringNull() if t := res.Get(path + "fileReputationCloudServer.optionType"); t.Exists() { @@ -211,14 +200,6 @@ func (data *PolicyObjectUnifiedAdvancedMalwareProtection) updateFromBody(ctx con data.Description = types.StringNull() } path := "payload.data." - data.MatchAllVpn = types.BoolNull() - - if t := res.Get(path + "matchAllVpn.optionType"); t.Exists() { - va := res.Get(path + "matchAllVpn.value") - if t.String() == "global" { - data.MatchAllVpn = types.BoolValue(va.Bool()) - } - } data.AmpCloudRegion = types.StringNull() if t := res.Get(path + "fileReputationCloudServer.optionType"); t.Exists() { @@ -284,9 +265,6 @@ func (data *PolicyObjectUnifiedAdvancedMalwareProtection) isNull(ctx context.Con if !data.FeatureProfileId.IsNull() { return false } - if !data.MatchAllVpn.IsNull() { - return false - } if !data.AmpCloudRegion.IsNull() { return false } diff --git a/internal/provider/model_sdwan_policy_object_unified_intrusion_prevention.go b/internal/provider/model_sdwan_policy_object_unified_intrusion_prevention.go index 9d5c9599..b6cabdf3 100644 --- a/internal/provider/model_sdwan_policy_object_unified_intrusion_prevention.go +++ b/internal/provider/model_sdwan_policy_object_unified_intrusion_prevention.go @@ -32,16 +32,16 @@ import ( // Section below is generated&owned by "gen/generator.go". //template:begin types type PolicyObjectUnifiedIntrusionPrevention struct { - Id types.String `tfsdk:"id"` - Version types.Int64 `tfsdk:"version"` - Name types.String `tfsdk:"name"` - Description types.String `tfsdk:"description"` - FeatureProfileId types.String `tfsdk:"feature_profile_id"` - SignatureSet types.String `tfsdk:"signature_set"` - InspectionMode types.String `tfsdk:"inspection_mode"` - IpsSignatureListId types.String `tfsdk:"ips_signature_list_id"` - LogLevel types.String `tfsdk:"log_level"` - CustomSignature types.Bool `tfsdk:"custom_signature"` + Id types.String `tfsdk:"id"` + Version types.Int64 `tfsdk:"version"` + Name types.String `tfsdk:"name"` + Description types.String `tfsdk:"description"` + FeatureProfileId types.String `tfsdk:"feature_profile_id"` + SignatureSet types.String `tfsdk:"signature_set"` + InspectionMode types.String `tfsdk:"inspection_mode"` + IpsSignatureAllowListId types.String `tfsdk:"ips_signature_allow_list_id"` + LogLevel types.String `tfsdk:"log_level"` + CustomSignature types.Bool `tfsdk:"custom_signature"` } // End of section. //template:end types @@ -78,10 +78,10 @@ func (data PolicyObjectUnifiedIntrusionPrevention) toBody(ctx context.Context) s body, _ = sjson.Set(body, path+"inspectionMode.value", data.InspectionMode.ValueString()) } } - if !data.IpsSignatureListId.IsNull() { + if !data.IpsSignatureAllowListId.IsNull() { if true { body, _ = sjson.Set(body, path+"signatureAllowedList.refId.optionType", "global") - body, _ = sjson.Set(body, path+"signatureAllowedList.refId.value", data.IpsSignatureListId.ValueString()) + body, _ = sjson.Set(body, path+"signatureAllowedList.refId.value", data.IpsSignatureAllowListId.ValueString()) } } if !data.LogLevel.IsNull() { @@ -126,12 +126,12 @@ func (data *PolicyObjectUnifiedIntrusionPrevention) fromBody(ctx context.Context data.InspectionMode = types.StringValue(va.String()) } } - data.IpsSignatureListId = types.StringNull() + data.IpsSignatureAllowListId = types.StringNull() if t := res.Get(path + "signatureAllowedList.refId.optionType"); t.Exists() { va := res.Get(path + "signatureAllowedList.refId.value") if t.String() == "global" { - data.IpsSignatureListId = types.StringValue(va.String()) + data.IpsSignatureAllowListId = types.StringValue(va.String()) } } data.LogLevel = types.StringNull() @@ -179,12 +179,12 @@ func (data *PolicyObjectUnifiedIntrusionPrevention) updateFromBody(ctx context.C data.InspectionMode = types.StringValue(va.String()) } } - data.IpsSignatureListId = types.StringNull() + data.IpsSignatureAllowListId = types.StringNull() if t := res.Get(path + "signatureAllowedList.refId.optionType"); t.Exists() { va := res.Get(path + "signatureAllowedList.refId.value") if t.String() == "global" { - data.IpsSignatureListId = types.StringValue(va.String()) + data.IpsSignatureAllowListId = types.StringValue(va.String()) } } data.LogLevel = types.StringNull() @@ -218,7 +218,7 @@ func (data *PolicyObjectUnifiedIntrusionPrevention) isNull(ctx context.Context, if !data.InspectionMode.IsNull() { return false } - if !data.IpsSignatureListId.IsNull() { + if !data.IpsSignatureAllowListId.IsNull() { return false } if !data.LogLevel.IsNull() { diff --git a/internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go b/internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go index c717b675..f8e8767c 100644 --- a/internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go +++ b/internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go @@ -37,7 +37,6 @@ type PolicyObjectUnifiedTLSSSLDecryption struct { Name types.String `tfsdk:"name"` Description types.String `tfsdk:"description"` FeatureProfileId types.String `tfsdk:"feature_profile_id"` - EnableSsl types.Bool `tfsdk:"enable_ssl"` ExpiredCertificate types.String `tfsdk:"expired_certificate"` UntrustedCertificate types.String `tfsdk:"untrusted_certificate"` CertificateRevocationStatus types.String `tfsdk:"certificate_revocation_status"` @@ -76,11 +75,9 @@ func (data PolicyObjectUnifiedTLSSSLDecryption) toBody(ctx context.Context) stri body, _ = sjson.Set(body, "name", data.Name.ValueString()) body, _ = sjson.Set(body, "description", data.Description.ValueString()) path := "data." - if !data.EnableSsl.IsNull() { - if true { - body, _ = sjson.Set(body, path+"sslEnable.optionType", "global") - body, _ = sjson.Set(body, path+"sslEnable.value", data.EnableSsl.ValueBool()) - } + if true { + body, _ = sjson.Set(body, path+"sslEnable.optionType", "global") + body, _ = sjson.Set(body, path+"sslEnable.value", true) } if !data.ExpiredCertificate.IsNull() { if true { @@ -101,7 +98,7 @@ func (data PolicyObjectUnifiedTLSSSLDecryption) toBody(ctx context.Context) stri } } if !data.UnknownRevocationStatus.IsNull() { - if true { + if true && data.CertificateRevocationStatus.ValueString() == "ocsp" { body, _ = sjson.Set(body, path+"unknownStatus.optionType", "global") body, _ = sjson.Set(body, path+"unknownStatus.value", data.UnknownRevocationStatus.ValueString()) } @@ -184,14 +181,6 @@ func (data *PolicyObjectUnifiedTLSSSLDecryption) fromBody(ctx context.Context, r data.Description = types.StringNull() } path := "payload.data." - data.EnableSsl = types.BoolNull() - - if t := res.Get(path + "sslEnable.optionType"); t.Exists() { - va := res.Get(path + "sslEnable.value") - if t.String() == "global" { - data.EnableSsl = types.BoolValue(va.Bool()) - } - } data.ExpiredCertificate = types.StringNull() if t := res.Get(path + "expiredCertificate.optionType"); t.Exists() { @@ -317,14 +306,6 @@ func (data *PolicyObjectUnifiedTLSSSLDecryption) updateFromBody(ctx context.Cont data.Description = types.StringNull() } path := "payload.data." - data.EnableSsl = types.BoolNull() - - if t := res.Get(path + "sslEnable.optionType"); t.Exists() { - va := res.Get(path + "sslEnable.value") - if t.String() == "global" { - data.EnableSsl = types.BoolValue(va.Bool()) - } - } data.ExpiredCertificate = types.StringNull() if t := res.Get(path + "expiredCertificate.optionType"); t.Exists() { @@ -446,9 +427,6 @@ func (data *PolicyObjectUnifiedTLSSSLDecryption) isNull(ctx context.Context, res if !data.FeatureProfileId.IsNull() { return false } - if !data.EnableSsl.IsNull() { - return false - } if !data.ExpiredCertificate.IsNull() { return false } diff --git a/internal/provider/model_sdwan_policy_object_unified_tls_ssl_profile.go b/internal/provider/model_sdwan_policy_object_unified_tls_ssl_profile.go index 0aafb56a..3348a2e8 100644 --- a/internal/provider/model_sdwan_policy_object_unified_tls_ssl_profile.go +++ b/internal/provider/model_sdwan_policy_object_unified_tls_ssl_profile.go @@ -102,13 +102,13 @@ func (data PolicyObjectUnifiedTLSSSLProfile) toBody(ctx context.Context) string } } if !data.DecryptThreshold.IsNull() { - if true { + if true && data.Reputation.ValueBool() == true { body, _ = sjson.Set(body, path+"decryptThreshold.optionType", "global") body, _ = sjson.Set(body, path+"decryptThreshold.value", data.DecryptThreshold.ValueString()) } } if !data.ThresholdCategories.IsNull() { - if true { + if true && data.Reputation.ValueBool() == true { body, _ = sjson.Set(body, path+"skipDecryptThreshold.optionType", "global") body, _ = sjson.Set(body, path+"skipDecryptThreshold.value", data.ThresholdCategories.ValueString()) } diff --git a/internal/provider/model_sdwan_policy_object_unified_url_filtering.go b/internal/provider/model_sdwan_policy_object_unified_url_filtering.go index 93c3cc31..e641cf9a 100644 --- a/internal/provider/model_sdwan_policy_object_unified_url_filtering.go +++ b/internal/provider/model_sdwan_policy_object_unified_url_filtering.go @@ -111,13 +111,13 @@ func (data PolicyObjectUnifiedURLFiltering) toBody(ctx context.Context) string { } } if !data.BlockPageContents.IsNull() { - if true { + if true && data.BlockPageAction.ValueString() == "text" { body, _ = sjson.Set(body, path+"blockPageContents.optionType", "global") body, _ = sjson.Set(body, path+"blockPageContents.value", data.BlockPageContents.ValueString()) } } if !data.RedirectUrl.IsNull() { - if true { + if true && data.BlockPageAction.ValueString() == "redirect-url" { body, _ = sjson.Set(body, path+"redirectUrl.optionType", "global") body, _ = sjson.Set(body, path+"redirectUrl.value", data.RedirectUrl.ValueString()) } @@ -129,7 +129,7 @@ func (data PolicyObjectUnifiedURLFiltering) toBody(ctx context.Context) string { } } if !data.Alerts.IsNull() { - if true { + if true && data.EnableAlerts.ValueBool() == true { body, _ = sjson.Set(body, path+"alerts.optionType", "global") var values []string data.Alerts.ElementsAs(ctx, &values, false) diff --git a/internal/provider/resource_sdwan_policy_object_security_protocol_list.go b/internal/provider/resource_sdwan_policy_object_security_protocol_list.go index a1c13e47..f188c06f 100644 --- a/internal/provider/resource_sdwan_policy_object_security_protocol_list.go +++ b/internal/provider/resource_sdwan_policy_object_security_protocol_list.go @@ -92,7 +92,7 @@ func (r *PolicyObjectSecurityProtocolListProfileParcelResource) Schema(ctx conte Required: true, NestedObject: schema.NestedAttributeObject{ Attributes: map[string]schema.Attribute{ - "protocol_names": schema.StringAttribute{ + "protocol_name": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("snmp", "icmp", "tcp", "udp", "echo", "telnet", "wins", "n2h2server", "nntp", "pptp", "rtsp", "bootpc", "gdoi", "tacacs", "gopher", "icabrowser", "skinny", "sunrpc", "biff", "router", "ircs", "orasrv", "ms-cluster-net", "kermit", "isakmp", "sshell", "realsecure", "ircu", "appleqtc", "pwdgen", "rdb-dbs-disp", "creativepartnr", "finger", "ftps", "giop", "rsvd", "hp-alarm-mgr", "uucp", "kerberos", "imap", "time", "bootps", "tftp", "oracle", "snmptrap", "http", "qmtp", "radius", "oracle-em-vp", "tarantella", "pcanywheredata", "ldap", "mgcp", "sqlsrv", "hsrp", "cisco-net-mgmt", "smtp", "pcanywherestat", "exec", "send", "stun", "syslog", "ms-sql-m", "citrix", "creativeserver", "cifs", "cisco-sys", "cisco-tna", "ms-dotnetster", "gtpv1", "gtpv0", "imap3", "fcip-port", "netbios-dgm", "sip-tls", "pop3s", "cisco-fna", "802-11-iapp", "oem-agent", "cisco-tdp", "tr-rsrb", "r-winsock", "sql-net", "syslog-conn", "tacacs-ds", "h225ras", "ace-svr", "dhcp-failover", "igmpv3lite", "irc-serv", "entrust-svcs", "dbcontrol_agent", "cisco-svcs", "ipsec-msft", "microsoft-ds", "ms-sna", "rsvp_tunnel", "rsvp-encap", "hp-collector", "netbios-ns", "msexch-routing", "h323", "l2tp", "ldap-admin", "pop3", "h323callsigalt", "ms-sql", "iscsi-target", "webster", "lotusnote", "ipx", "entrust-svc-hand", "citriximaclient", "rtc-pm-port", "ftp", "aol", "xdmcp", "oraclenames", "login", "iscsi", "ttc", "imaps", "socks", "ssh", "dnsix", "daytime", "sip", "discard", "ntp", "ldaps", "https", "vdolive", "ica", "net8-cman", "cuseeme", "netstat", "sms", "streamworks", "rtelnet", "who", "kazaa", "ssp", "dbase", "timed", "cddbp", "telnets", "ymsgr", "ident", "bgp", "ddns-v3", "vqp", "irc", "ipass", "x11", "dns", "lotusmtap", "mysql", "nfs", "msnmsgr", "netshow", "sqlserv", "hp-managed-node", "ncp", "shell", "realmedia", "msrpc", "clp").String, Optional: true, Validators: []validator.String{ diff --git a/internal/provider/resource_sdwan_policy_object_security_protocol_list_test.go b/internal/provider/resource_sdwan_policy_object_security_protocol_list_test.go index 70a2e6f1..8c965948 100644 --- a/internal/provider/resource_sdwan_policy_object_security_protocol_list_test.go +++ b/internal/provider/resource_sdwan_policy_object_security_protocol_list_test.go @@ -33,7 +33,7 @@ func TestAccSdwanPolicyObjectSecurityProtocolListProfileParcel(t *testing.T) { t.Skip("skipping test, set environment variable SDWAN_2012") } var checks []resource.TestCheckFunc - checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_security_protocol_list.test", "entries.0.protocol_names", "aol")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_security_protocol_list.test", "entries.0.protocol_name", "aol")) resource.Test(t, resource.TestCase{ PreCheck: func() { testAccPreCheck(t) }, ProtoV6ProviderFactories: testAccProtoV6ProviderFactories, @@ -70,7 +70,7 @@ func testAccSdwanPolicyObjectSecurityProtocolListProfileParcelConfig_all() strin config += ` description = "Terraform integration test"` + "\n" config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" config += ` entries = [{` + "\n" - config += ` protocol_names = "aol"` + "\n" + config += ` protocol_name = "aol"` + "\n" config += ` }]` + "\n" config += `}` + "\n" return config diff --git a/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile.go b/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile.go index 06884f1a..d88a744e 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile.go +++ b/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile.go @@ -97,28 +97,28 @@ func (r *PolicyObjectUnifiedAdvancedInspectionProfileProfileParcelResource) Sche }, "intrusion_prevention_list_id": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, + Optional: true, Validators: []validator.String{ stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), }, }, "url_filtering_list_id": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, + Optional: true, Validators: []validator.String{ stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), }, }, "advanced_malware_protection_list_id": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, + Optional: true, Validators: []validator.String{ stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), }, }, "tls_ssl_profile_list_id": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, + Optional: true, Validators: []validator.String{ stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), }, diff --git a/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go b/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go index 3f1e7da1..d2ea4462 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go +++ b/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go @@ -121,7 +121,6 @@ resource "sdwan_policy_object_unified_advanced_malware_protection" "test" { name = "TF_TEST_ADVANCED_MALWARE" description = "My Example" feature_profile_id = sdwan_policy_object_feature_profile.test.id - match_all_vpn = true amp_cloud_region = "nam" amp_cloud_region_est_server = "nam" alert_log_level = "critical" diff --git a/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection.go b/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection.go index e3aed7bf..04f60c95 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection.go +++ b/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection.go @@ -87,10 +87,6 @@ func (r *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource) Sche MarkdownDescription: helpers.NewAttributeDescription("Feature Profile ID").String, Required: true, }, - "match_all_vpn": schema.BoolAttribute{ - MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, - }, "amp_cloud_region": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("nam", "eur", "apjc").String, Required: true, @@ -117,20 +113,20 @@ func (r *PolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelResource) Sche Required: true, }, "file_analysis_cloud_region": schema.StringAttribute{ - MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("nam", "eur").String, - Required: true, + MarkdownDescription: helpers.NewAttributeDescription(", Attribute conditional on `file_analysis` being equal to `true`").AddStringEnumDescription("nam", "eur").String, + Optional: true, Validators: []validator.String{ stringvalidator.OneOf("nam", "eur"), }, }, "file_analysis_file_types": schema.SetAttribute{ - MarkdownDescription: helpers.NewAttributeDescription("").String, + MarkdownDescription: helpers.NewAttributeDescription(", Attribute conditional on `file_analysis` being equal to `true`").String, ElementType: types.StringType, - Required: true, + Optional: true, }, "file_analysis_alert_log_level": schema.StringAttribute{ - MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("critical", "warning", "info").String, - Required: true, + MarkdownDescription: helpers.NewAttributeDescription(", Attribute conditional on `file_analysis` being equal to `true`").AddStringEnumDescription("critical", "warning", "info").String, + Optional: true, Validators: []validator.String{ stringvalidator.OneOf("critical", "warning", "info"), }, diff --git a/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection_test.go b/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection_test.go index eb555f23..61d8b3c7 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection_test.go +++ b/internal/provider/resource_sdwan_policy_object_unified_advanced_malware_protection_test.go @@ -33,7 +33,6 @@ func TestAccSdwanPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcel(t *te t.Skip("skipping test, set environment variable SDWAN_2012") } var checks []resource.TestCheckFunc - checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_malware_protection.test", "match_all_vpn", "true")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_malware_protection.test", "amp_cloud_region", "nam")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_malware_protection.test", "amp_cloud_region_est_server", "nam")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_advanced_malware_protection.test", "alert_log_level", "critical")) @@ -76,7 +75,6 @@ func testAccSdwanPolicyObjectUnifiedAdvancedMalwareProtectionProfileParcelConfig config += ` name = "TF_TEST_ALL"` + "\n" config += ` description = "Terraform integration test"` + "\n" config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" - config += ` match_all_vpn = true` + "\n" config += ` amp_cloud_region = "nam"` + "\n" config += ` amp_cloud_region_est_server = "nam"` + "\n" config += ` alert_log_level = "critical"` + "\n" diff --git a/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention.go b/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention.go index b92f9787..41309456 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention.go +++ b/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention.go @@ -102,9 +102,9 @@ func (r *PolicyObjectUnifiedIntrusionPreventionProfileParcelResource) Schema(ctx stringvalidator.OneOf("detection", "protection"), }, }, - "ips_signature_list_id": schema.StringAttribute{ + "ips_signature_allow_list_id": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, + Optional: true, Validators: []validator.String{ stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), }, @@ -118,7 +118,7 @@ func (r *PolicyObjectUnifiedIntrusionPreventionProfileParcelResource) Schema(ctx }, "custom_signature": schema.BoolAttribute{ MarkdownDescription: helpers.NewAttributeDescription("Can be one of the enum value").String, - Required: true, + Optional: true, }, }, } diff --git a/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention_test.go b/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention_test.go index c5da0b00..9a04abba 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention_test.go +++ b/internal/provider/resource_sdwan_policy_object_unified_intrusion_prevention_test.go @@ -87,7 +87,7 @@ func testAccSdwanPolicyObjectUnifiedIntrusionPreventionProfileParcelConfig_all() config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" config += ` signature_set = "balanced"` + "\n" config += ` inspection_mode = "detection"` + "\n" - config += ` ips_signature_list_id = sdwan_policy_object_security_ips_signature.test.id` + "\n" + config += ` ips_signature_allow_list_id = sdwan_policy_object_security_ips_signature.test.id` + "\n" config += ` log_level = "error"` + "\n" config += ` custom_signature = false` + "\n" config += `}` + "\n" diff --git a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption.go b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption.go index e64113aa..58ff8068 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption.go +++ b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption.go @@ -87,10 +87,6 @@ func (r *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource) Schema(ctx co MarkdownDescription: helpers.NewAttributeDescription("Feature Profile ID").String, Required: true, }, - "enable_ssl": schema.BoolAttribute{ - MarkdownDescription: helpers.NewAttributeDescription("If false, no other fields should be provided, if true all fields should be provided").String, - Required: true, - }, "expired_certificate": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("decrypt", "drop").String, Required: true, @@ -113,8 +109,8 @@ func (r *PolicyObjectUnifiedTLSSSLDecryptionProfileParcelResource) Schema(ctx co }, }, "unknown_revocation_status": schema.StringAttribute{ - MarkdownDescription: helpers.NewAttributeDescription("Only required if certificateRevocationStatus is oscp, if value is none then field shouldn't be here").AddStringEnumDescription("decrypt", "drop").String, - Required: true, + MarkdownDescription: helpers.NewAttributeDescription("Only required if certificateRevocationStatus is oscp, if value is none then field shouldn't be here, Attribute conditional on `certificate_revocation_status` being equal to `ocsp`").AddStringEnumDescription("decrypt", "drop").String, + Optional: true, Validators: []validator.String{ stringvalidator.OneOf("decrypt", "drop"), }, diff --git a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go index 3fd3f08b..35a8e2bc 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go +++ b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go @@ -33,12 +33,11 @@ func TestAccSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcel(t *testing.T) t.Skip("skipping test, set environment variable SDWAN_2012") } var checks []resource.TestCheckFunc - checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "enable_ssl", "true")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "expired_certificate", "drop")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "untrusted_certificate", "drop")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "certificate_revocation_status", "ocsp")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "unknown_revocation_status", "decrypt")) - checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_protocol_versions", "no-decrypt")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_protocol_versions", "drop")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_cipher_suites", "drop")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "failure_mode", "close")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "default_ca_certificate_bundle", "true")) @@ -81,12 +80,11 @@ func testAccSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcelConfig_all() st config += ` name = "TF_TEST_ALL"` + "\n" config += ` description = "Terraform integration test"` + "\n" config += ` feature_profile_id = sdwan_policy_object_feature_profile.test.id` + "\n" - config += ` enable_ssl = true` + "\n" config += ` expired_certificate = "drop"` + "\n" config += ` untrusted_certificate = "drop"` + "\n" config += ` certificate_revocation_status = "ocsp"` + "\n" config += ` unknown_revocation_status = "decrypt"` + "\n" - config += ` unsupported_protocol_versions = "no-decrypt"` + "\n" + config += ` unsupported_protocol_versions = "drop"` + "\n" config += ` unsupported_cipher_suites = "drop"` + "\n" config += ` failure_mode = "close"` + "\n" config += ` default_ca_certificate_bundle = true` + "\n" diff --git a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile.go b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile.go index c85d05ed..5f4d3697 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile.go +++ b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_profile.go @@ -108,15 +108,15 @@ func (r *PolicyObjectUnifiedTLSSSLProfileProfileParcelResource) Schema(ctx conte Required: true, }, "decrypt_threshold": schema.StringAttribute{ - MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy").String, - Required: true, + MarkdownDescription: helpers.NewAttributeDescription(", Attribute conditional on `reputation` being equal to `true`").AddStringEnumDescription("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy").String, + Optional: true, Validators: []validator.String{ stringvalidator.OneOf("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy"), }, }, "threshold_categories": schema.StringAttribute{ - MarkdownDescription: helpers.NewAttributeDescription("").AddStringEnumDescription("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy").String, - Required: true, + MarkdownDescription: helpers.NewAttributeDescription(", Attribute conditional on `reputation` being equal to `true`").AddStringEnumDescription("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy").String, + Optional: true, Validators: []validator.String{ stringvalidator.OneOf("high-risk", "low-risk", "moderate-risk", "suspicious", "trustworthy"), }, @@ -127,14 +127,14 @@ func (r *PolicyObjectUnifiedTLSSSLProfileProfileParcelResource) Schema(ctx conte }, "url_allow_list_id": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, + Optional: true, Validators: []validator.String{ stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), }, }, "url_block_list_id": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, + Optional: true, Validators: []validator.String{ stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), }, diff --git a/internal/provider/resource_sdwan_policy_object_unified_url_filtering.go b/internal/provider/resource_sdwan_policy_object_unified_url_filtering.go index e52ec2ee..ef212fc7 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_url_filtering.go +++ b/internal/provider/resource_sdwan_policy_object_unified_url_filtering.go @@ -109,14 +109,14 @@ func (r *PolicyObjectUnifiedURLFilteringProfileParcelResource) Schema(ctx contex }, "url_allow_list_id": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, + Optional: true, Validators: []validator.String{ stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), }, }, "url_block_list_id": schema.StringAttribute{ MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, + Optional: true, Validators: []validator.String{ stringvalidator.RegexMatches(regexp.MustCompile(`[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}`), ""), }, @@ -129,12 +129,12 @@ func (r *PolicyObjectUnifiedURLFilteringProfileParcelResource) Schema(ctx contex }, }, "block_page_contents": schema.StringAttribute{ - MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, + MarkdownDescription: helpers.NewAttributeDescription(", Attribute conditional on `block_page_action` being equal to `text`").String, + Optional: true, }, "redirect_url": schema.StringAttribute{ - MarkdownDescription: helpers.NewAttributeDescription("").String, - Required: true, + MarkdownDescription: helpers.NewAttributeDescription(", Attribute conditional on `block_page_action` being equal to `redirect-url`").String, + Optional: true, Validators: []validator.String{ stringvalidator.RegexMatches(regexp.MustCompile(`^(http://www\.|https://www\.|http://|https://)?[a-z0-9]+([\-\.]{1}[a-z0-9]+)*\.[a-z]{2,5}(:[0-9]{1,5})?(/.*)?$`), ""), }, @@ -144,9 +144,9 @@ func (r *PolicyObjectUnifiedURLFilteringProfileParcelResource) Schema(ctx contex Required: true, }, "alerts": schema.SetAttribute{ - MarkdownDescription: helpers.NewAttributeDescription("").String, + MarkdownDescription: helpers.NewAttributeDescription(", Attribute conditional on `enable_alerts` being equal to `true`").String, ElementType: types.StringType, - Required: true, + Optional: true, }, }, } diff --git a/internal/provider/resource_sdwan_policy_object_unified_url_filtering_test.go b/internal/provider/resource_sdwan_policy_object_unified_url_filtering_test.go index faad1e6f..609670c2 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_url_filtering_test.go +++ b/internal/provider/resource_sdwan_policy_object_unified_url_filtering_test.go @@ -37,7 +37,6 @@ func TestAccSdwanPolicyObjectUnifiedURLFilteringProfileParcel(t *testing.T) { checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_url_filtering.test", "web_reputation", "suspicious")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_url_filtering.test", "block_page_action", "text")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_url_filtering.test", "block_page_contents", "Access to the requested page has been denied. Please contact your Network Administrator")) - checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_url_filtering.test", "redirect_url", "www.example.com")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_url_filtering.test", "enable_alerts", "true")) resource.Test(t, resource.TestCase{ PreCheck: func() { testAccPreCheck(t) }, @@ -103,7 +102,6 @@ func testAccSdwanPolicyObjectUnifiedURLFilteringProfileParcelConfig_all() string config += ` url_block_list_id = sdwan_policy_object_security_url_block_list.test.id` + "\n" config += ` block_page_action = "text"` + "\n" config += ` block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator"` + "\n" - config += ` redirect_url = "www.example.com"` + "\n" config += ` enable_alerts = true` + "\n" config += ` alerts = ["blacklist"]` + "\n" config += `}` + "\n" From 9e62cafa60d0a53c01ded5d5992bb3e6fa93a0f2 Mon Sep 17 00:00:00 2001 From: Sean Conroy Date: Wed, 20 Nov 2024 13:58:38 +0000 Subject: [PATCH 10/11] Update policy object security port list id issue --- .../policy_object_security_protocol_list.yaml | 1 + .../resource_sdwan_policy_object_security_protocol_list.go | 6 +----- 2 files changed, 2 insertions(+), 5 deletions(-) diff --git a/gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml b/gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml index 77ae9978..4d51d186 100644 --- a/gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml +++ b/gen/definitions/profile_parcels/policy_object_security_protocol_list.yaml @@ -5,6 +5,7 @@ minimum_version: 20.12.0 test_tags: [SDWAN_2012] skip_minimum_test: true parcel_type: policy_object +full_update: true attributes: - tf_name: feature_profile_id reference: true diff --git a/internal/provider/resource_sdwan_policy_object_security_protocol_list.go b/internal/provider/resource_sdwan_policy_object_security_protocol_list.go index a46969cf..f2cba9c1 100644 --- a/internal/provider/resource_sdwan_policy_object_security_protocol_list.go +++ b/internal/provider/resource_sdwan_policy_object_security_protocol_list.go @@ -174,11 +174,7 @@ func (r *PolicyObjectSecurityProtocolListProfileParcelResource) Read(ctx context } // If every attribute is set to null we are dealing with an import operation and therefore reading all attributes - if state.isNull(ctx, res) { - state.fromBody(ctx, res) - } else { - state.updateFromBody(ctx, res) - } + state.fromBody(ctx, res) if state.Version.IsNull() { state.Version = types.Int64Value(0) } From 1750c7671d9ffe01a883e681e575f0169dad3c97 Mon Sep 17 00:00:00 2001 From: Sean Conroy Date: Thu, 21 Nov 2024 12:52:12 +0000 Subject: [PATCH 11/11] Fix testing issue --- ...olicy_object_unified_tls_ssl_decryption.md | 2 +- .../resource.tf | 2 +- ...t_unified_advanced_inspection_profile.yaml | 23 ++++++++----------- ...icy_object_unified_tls_ssl_decryption.yaml | 6 ++--- ...nified_advanced_inspection_profile_test.go | 23 ++++++++----------- ..._object_unified_tls_ssl_decryption_test.go | 4 ++-- ...olicy_object_unified_tls_ssl_decryption.go | 2 +- ...nified_advanced_inspection_profile_test.go | 23 ++++++++----------- ..._object_unified_tls_ssl_decryption_test.go | 4 ++-- 9 files changed, 40 insertions(+), 49 deletions(-) diff --git a/docs/resources/policy_object_unified_tls_ssl_decryption.md b/docs/resources/policy_object_unified_tls_ssl_decryption.md index af3d2620..aa7bb879 100644 --- a/docs/resources/policy_object_unified_tls_ssl_decryption.md +++ b/docs/resources/policy_object_unified_tls_ssl_decryption.md @@ -23,7 +23,7 @@ resource "sdwan_policy_object_unified_tls_ssl_decryption" "example" { untrusted_certificate = "drop" certificate_revocation_status = "ocsp" unknown_revocation_status = "decrypt" - unsupported_protocol_versions = "drop" + unsupported_protocol_versions = "no-decrypt" unsupported_cipher_suites = "drop" failure_mode = "close" default_ca_certificate_bundle = true diff --git a/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf b/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf index 86e48f19..8aed866c 100644 --- a/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf +++ b/examples/resources/sdwan_policy_object_unified_tls_ssl_decryption/resource.tf @@ -6,7 +6,7 @@ resource "sdwan_policy_object_unified_tls_ssl_decryption" "example" { untrusted_certificate = "drop" certificate_revocation_status = "ocsp" unknown_revocation_status = "decrypt" - unsupported_protocol_versions = "drop" + unsupported_protocol_versions = "no-decrypt" unsupported_cipher_suites = "drop" failure_mode = "close" default_ca_certificate_bundle = true diff --git a/gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml b/gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml index 6af9a37f..b8f73bda 100644 --- a/gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml +++ b/gen/definitions/profile_parcels/policy_object_unified_advanced_inspection_profile.yaml @@ -68,18 +68,15 @@ test_prerequisites: | ] } - resource "sdwan_policy_object_unified_url_filtering" "test" { - name = "TF_TEST_URL_FILTERING" + resource "sdwan_policy_object_unified_url_filtering" "example" { + name = "Example" description = "My Example" feature_profile_id = sdwan_policy_object_feature_profile.test.id web_categories_action = "block" web_categories = ["confirmed-spam-sources"] web_reputation = "suspicious" - url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id - url_block_list_id = sdwan_policy_object_security_url_block_list.test.id block_page_action = "text" block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator" - redirect_url = "www.example.com" enable_alerts = true alerts = ["blacklist"] } @@ -97,14 +94,14 @@ test_prerequisites: | } resource "sdwan_policy_object_unified_intrusion_prevention" "test" { - name = "TF_TEST_INTRUSION" - description = "My Example" - feature_profile_id = sdwan_policy_object_feature_profile.test.id - signature_set = "balanced" - inspection_mode = "detection" - ips_signature_list_id = sdwan_policy_object_security_ips_signature.test.id - log_level = "error" - custom_signature = false + name = "TF_TEST_INTRUSION" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + signature_set = "balanced" + inspection_mode = "detection" + ips_signature_allow_list_id = sdwan_policy_object_security_ips_signature.test.id + log_level = "error" + custom_signature = false } resource "sdwan_policy_object_unified_advanced_malware_protection" "test" { diff --git a/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml b/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml index 4801eaad..ca27b2ac 100644 --- a/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml +++ b/gen/definitions/profile_parcels/policy_object_unified_tls_ssl_decryption.yaml @@ -14,10 +14,8 @@ attributes: example: f6dd22c8-0b4f-496c-9a0b-6813d1f8b8ac test_value: sdwan_policy_object_feature_profile.test.id - model_name: sslEnable - tf_name: enable_ssl value: true value_type: "global" - example: true - model_name: expiredCertificate example: drop @@ -25,6 +23,7 @@ attributes: example: drop - model_name: certificateRevocationStatus + tf_name: certificate_revocation_status example: ocsp - model_name: unknownStatus tf_name: unknown_revocation_status @@ -36,7 +35,7 @@ attributes: - model_name: unsupportedProtocolVersions - example: drop + example: no-decrypt - model_name: unsupportedCipherSuites example: drop - model_name: failureMode @@ -72,6 +71,7 @@ attributes: example: TLSv1.2 - model_name: caTpLabel + value_type: "global" value: PROXY-SIGNING-CA test_prerequisites: | diff --git a/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go b/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go index 5d26b518..6abc01c2 100644 --- a/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go +++ b/internal/provider/data_source_sdwan_policy_object_unified_advanced_inspection_profile_test.go @@ -77,18 +77,15 @@ resource "sdwan_policy_object_security_url_block_list" "test" { ] } -resource "sdwan_policy_object_unified_url_filtering" "test" { - name = "TF_TEST_URL_FILTERING" +resource "sdwan_policy_object_unified_url_filtering" "example" { + name = "Example" description = "My Example" feature_profile_id = sdwan_policy_object_feature_profile.test.id web_categories_action = "block" web_categories = ["confirmed-spam-sources"] web_reputation = "suspicious" - url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id - url_block_list_id = sdwan_policy_object_security_url_block_list.test.id block_page_action = "text" block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator" - redirect_url = "www.example.com" enable_alerts = true alerts = ["blacklist"] } @@ -106,14 +103,14 @@ resource "sdwan_policy_object_security_ips_signature" "test" { } resource "sdwan_policy_object_unified_intrusion_prevention" "test" { - name = "TF_TEST_INTRUSION" - description = "My Example" - feature_profile_id = sdwan_policy_object_feature_profile.test.id - signature_set = "balanced" - inspection_mode = "detection" - ips_signature_list_id = sdwan_policy_object_security_ips_signature.test.id - log_level = "error" - custom_signature = false + name = "TF_TEST_INTRUSION" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + signature_set = "balanced" + inspection_mode = "detection" + ips_signature_allow_list_id = sdwan_policy_object_security_ips_signature.test.id + log_level = "error" + custom_signature = false } resource "sdwan_policy_object_unified_advanced_malware_protection" "test" { diff --git a/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go index 4df6545f..2caae294 100644 --- a/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go +++ b/internal/provider/data_source_sdwan_policy_object_unified_tls_ssl_decryption_test.go @@ -37,7 +37,7 @@ func TestAccDataSourceSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcel(t *t checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "untrusted_certificate", "drop")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "certificate_revocation_status", "ocsp")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "unknown_revocation_status", "decrypt")) - checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_protocol_versions", "drop")) + checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_protocol_versions", "no-decrypt")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_cipher_suites", "drop")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "failure_mode", "close")) checks = append(checks, resource.TestCheckResourceAttr("data.sdwan_policy_object_unified_tls_ssl_decryption.test", "default_ca_certificate_bundle", "true")) @@ -79,7 +79,7 @@ func testAccDataSourceSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcelConfi config += ` untrusted_certificate = "drop"` + "\n" config += ` certificate_revocation_status = "ocsp"` + "\n" config += ` unknown_revocation_status = "decrypt"` + "\n" - config += ` unsupported_protocol_versions = "drop"` + "\n" + config += ` unsupported_protocol_versions = "no-decrypt"` + "\n" config += ` unsupported_cipher_suites = "drop"` + "\n" config += ` failure_mode = "close"` + "\n" config += ` default_ca_certificate_bundle = true` + "\n" diff --git a/internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go b/internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go index f8e8767c..8d1a4dd2 100644 --- a/internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go +++ b/internal/provider/model_sdwan_policy_object_unified_tls_ssl_decryption.go @@ -164,7 +164,7 @@ func (data PolicyObjectUnifiedTLSSSLDecryption) toBody(ctx context.Context) stri } } if true { - body, _ = sjson.Set(body, path+"caTpLabel.optionType", "default") + body, _ = sjson.Set(body, path+"caTpLabel.optionType", "global") body, _ = sjson.Set(body, path+"caTpLabel.value", "PROXY-SIGNING-CA") } return body diff --git a/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go b/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go index d2ea4462..2cafe419 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go +++ b/internal/provider/resource_sdwan_policy_object_unified_advanced_inspection_profile_test.go @@ -78,18 +78,15 @@ resource "sdwan_policy_object_security_url_block_list" "test" { ] } -resource "sdwan_policy_object_unified_url_filtering" "test" { - name = "TF_TEST_URL_FILTERING" +resource "sdwan_policy_object_unified_url_filtering" "example" { + name = "Example" description = "My Example" feature_profile_id = sdwan_policy_object_feature_profile.test.id web_categories_action = "block" web_categories = ["confirmed-spam-sources"] web_reputation = "suspicious" - url_allow_list_id = sdwan_policy_object_security_url_allow_list.test.id - url_block_list_id = sdwan_policy_object_security_url_block_list.test.id block_page_action = "text" block_page_contents = "Access to the requested page has been denied. Please contact your Network Administrator" - redirect_url = "www.example.com" enable_alerts = true alerts = ["blacklist"] } @@ -107,14 +104,14 @@ resource "sdwan_policy_object_security_ips_signature" "test" { } resource "sdwan_policy_object_unified_intrusion_prevention" "test" { - name = "TF_TEST_INTRUSION" - description = "My Example" - feature_profile_id = sdwan_policy_object_feature_profile.test.id - signature_set = "balanced" - inspection_mode = "detection" - ips_signature_list_id = sdwan_policy_object_security_ips_signature.test.id - log_level = "error" - custom_signature = false + name = "TF_TEST_INTRUSION" + description = "My Example" + feature_profile_id = sdwan_policy_object_feature_profile.test.id + signature_set = "balanced" + inspection_mode = "detection" + ips_signature_allow_list_id = sdwan_policy_object_security_ips_signature.test.id + log_level = "error" + custom_signature = false } resource "sdwan_policy_object_unified_advanced_malware_protection" "test" { diff --git a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go index 35a8e2bc..ce9ccf98 100644 --- a/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go +++ b/internal/provider/resource_sdwan_policy_object_unified_tls_ssl_decryption_test.go @@ -37,7 +37,7 @@ func TestAccSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcel(t *testing.T) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "untrusted_certificate", "drop")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "certificate_revocation_status", "ocsp")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "unknown_revocation_status", "decrypt")) - checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_protocol_versions", "drop")) + checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_protocol_versions", "no-decrypt")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "unsupported_cipher_suites", "drop")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "failure_mode", "close")) checks = append(checks, resource.TestCheckResourceAttr("sdwan_policy_object_unified_tls_ssl_decryption.test", "default_ca_certificate_bundle", "true")) @@ -84,7 +84,7 @@ func testAccSdwanPolicyObjectUnifiedTLSSSLDecryptionProfileParcelConfig_all() st config += ` untrusted_certificate = "drop"` + "\n" config += ` certificate_revocation_status = "ocsp"` + "\n" config += ` unknown_revocation_status = "decrypt"` + "\n" - config += ` unsupported_protocol_versions = "drop"` + "\n" + config += ` unsupported_protocol_versions = "no-decrypt"` + "\n" config += ` unsupported_cipher_suites = "drop"` + "\n" config += ` failure_mode = "close"` + "\n" config += ` default_ca_certificate_bundle = true` + "\n"