diff --git a/Packs/PAN-OS/Integrations/Panorama/Panorama.py b/Packs/PAN-OS/Integrations/Panorama/Panorama.py
index 748ad0582192..c73cee6d3f78 100644
--- a/Packs/PAN-OS/Integrations/Panorama/Panorama.py
+++ b/Packs/PAN-OS/Integrations/Panorama/Panorama.py
@@ -214,6 +214,12 @@
'file-forward',
'is-saas')
+RULE_TYPES_MAP = {
+ "Security Rule": "security",
+ "NAT Rule": "nat",
+ "PBF Rule": "pbf"
+}
+
class PAN_OS_Not_Found(Exception):
""" PAN-OS Error. """
@@ -688,9 +694,9 @@ def prepare_security_rule_params(api_action: str = None, rulename: str = None, s
raise Exception('Please provide the pre_post argument when configuring '
'a security rule in Panorama instance.')
else:
- params['xpath'] = f"{XPATH_SECURITY_RULES}{PRE_POST}/security/rules/entry[@name='{rulename}']"
+ params['xpath'] = f"{XPATH_RULEBASE}{PRE_POST}/security/rules/entry[@name='{rulename}']"
else:
- params['xpath'] = f"{XPATH_SECURITY_RULES}[@name='{rulename}']"
+ params['xpath'] = f"{XPATH_RULEBASE}[@name='{rulename}']"
return params
@@ -1542,6 +1548,8 @@ def prettify_addresses_arr(addresses_arr: list) -> List:
pretty_address['IP_Netmask'] = address['ip-netmask']
if 'ip-range' in address:
pretty_address['IP_Range'] = address['ip-range']
+ if 'ip-wildcard' in address:
+ pretty_address['IP_Wildcard'] = address['ip-wildcard']
if 'fqdn' in address:
pretty_address['FQDN'] = address['fqdn']
if 'tag' in address and address['tag'] is not None and 'member' in address['tag']:
@@ -1588,7 +1596,8 @@ def panorama_list_addresses_command(args: dict):
'Contents': addresses_arr,
'ReadableContentsFormat': formats['markdown'],
'HumanReadable': tableToMarkdown('Addresses:', addresses_output,
- ['Name', 'IP_Netmask', 'IP_Range', 'FQDN', 'Tags'], removeNull=True),
+ ['Name', 'IP_Netmask', 'IP_Range', 'IP_Wildcard', 'FQDN', 'Tags'],
+ removeNull=True),
'EntryContext': {
"Panorama.Addresses(val.Name == obj.Name)": addresses_output
}
@@ -3865,6 +3874,10 @@ def panorama_create_rule_command(args: dict):
log_forwarding=log_forwarding, tags=tags, category=categories,
from_=source_zone, to=destination_zone, profile_setting=profile_setting,
where=where, dst=dst)
+
+ if args.get('audit_comment'):
+ params['audit-comment'] = args.get('audit_comment')
+
result = http_request(
URL,
'POST',
@@ -4005,7 +4018,7 @@ def panorama_edit_rule_items(rulename: str, element_to_change: str, element_valu
def build_audit_comment_params(
- name: str, audit_comment: str, pre_post: str, policy_type='security'
+ name: str, pre_post: str, audit_comment: str = '', policy_type='security', xml_type='set'
) -> dict:
"""
Builds up the params needed to update the audit comment of a policy rule.
@@ -4013,11 +4026,22 @@ def build_audit_comment_params(
_xpath = f"{XPATH_RULEBASE}{pre_post}/{policy_type}/rules/entry[@name='{name}']"
return {
'type': 'op',
- 'cmd': f"{_xpath}{audit_comment}",
+ 'cmd': build_audit_comment_cmd(_xpath, audit_comment, xml_type),
'key': API_KEY
}
+def build_audit_comment_cmd(xpath, audit_comment, xml_type='set') -> str:
+ """
+ Builds up the needed `cmd` param to get or update the audit comment of a policy rule.
+ """
+ if xml_type == 'set':
+ return f"{xpath}{audit_comment}"
+ elif xml_type == 'show':
+ return f"{xpath}
"
+ return ""
+
+
@logger
def panorama_edit_rule_command(args: dict):
"""
@@ -4046,7 +4070,7 @@ def panorama_edit_rule_command(args: dict):
new_audit_comment = args.get('element_value') or ''
# to update audit-comment of a security rule, it is required to build a 'cmd' parameter
params = build_audit_comment_params(
- rulename, new_audit_comment, pre_post='rulebase' if VSYS else pre_post
+ rulename, pre_post='rulebase' if VSYS else pre_post, audit_comment=new_audit_comment
)
else:
params = {
@@ -12327,6 +12351,9 @@ def _set_up_original_packet_objects_body_request():
'key': API_KEY
}
+ if args.get('audit_comment'):
+ params['audit-comment'] = args.get('audit_comment')
+
return http_request(URL, 'POST', params=params)
@@ -12370,22 +12397,28 @@ def pan_os_edit_nat_rule(
):
xpath = build_nat_xpath(name=rule_name, pre_post='rulebase' if VSYS else pre_post, element=element_to_change)
- params = {
- 'xpath': xpath,
- 'element': dict_to_xml(build_body_request_to_edit_pan_os_object(
- behavior=behavior,
- object_name=object_name,
- element_value=element_value,
- is_listable=is_listable,
- xpath=xpath,
- should_contain_entries=True,
- is_commit_required=False
+ if element_to_change == 'audit-comment':
+ # to update audit-comment of a nat rule, it is required to build a 'cmd' parameter
+ params = build_audit_comment_params(
+ rule_name, pre_post='rulebase' if VSYS else pre_post, audit_comment=element_value, policy_type='nat'
)
- ),
- 'action': 'edit',
- 'type': 'config',
- 'key': API_KEY
- }
+ else:
+ params = {
+ 'xpath': xpath,
+ 'element': dict_to_xml(build_body_request_to_edit_pan_os_object(
+ behavior=behavior,
+ object_name=object_name,
+ element_value=element_value,
+ is_listable=is_listable,
+ xpath=xpath,
+ should_contain_entries=True,
+ is_commit_required=False
+ )
+ ),
+ 'action': 'edit',
+ 'type': 'config',
+ 'key': API_KEY
+ }
return http_request(URL, 'POST', params=params)
@@ -12451,7 +12484,8 @@ def pan_os_edit_nat_rule_command(args):
'dynamic-destination-translation/distribution', 'distribution', False
),
'destination_translation_port': ('destination-translation/translated-port', 'translated-port', False),
- 'destination_translation_ip': ('destination-translation/translated-address', 'translated-address', False)
+ 'destination_translation_ip': ('destination-translation/translated-address', 'translated-address', False),
+ 'audit-comment': ('audit-comment', '', False)
}
element_to_change, object_name, is_listable = elements_to_change_mapping_pan_os_paths.get(
@@ -13038,6 +13072,9 @@ def _setup_general_rule_body_request():
'key': API_KEY
}
+ if args.get('audit_comment'):
+ params['audit-comment'] = args.get('audit_comment')
+
return http_request(URL, 'POST', params=params)
@@ -13058,23 +13095,29 @@ def pan_os_edit_pbf_rule(
name=rule_name, pre_post='rulebase' if VSYS else pre_post, element_to_change=element_to_change
)
- params = {
- 'xpath': xpath,
- 'element': dict_to_xml(build_body_request_to_edit_pan_os_object(
- behavior=behavior,
- object_name=object_name,
- element_value=element_value,
- is_listable=is_listable,
- xpath=xpath,
- is_entry=True if object_name == 'nexthop-address-list' else False,
- is_empty_tag=True if object_name == 'action' else False
- ),
- contains_xml_chars=True
- ),
- 'action': 'edit',
- 'type': 'config',
- 'key': API_KEY
- }
+ if element_to_change == 'audit-comment':
+ # to update audit-comment of a pbf rule, it is required to build a 'cmd' parameter
+ params = build_audit_comment_params(
+ rule_name, pre_post='rulebase' if VSYS else pre_post, audit_comment=element_value, policy_type='pbf'
+ )
+ else:
+ params = {
+ 'xpath': xpath,
+ 'element': dict_to_xml(build_body_request_to_edit_pan_os_object(
+ behavior=behavior,
+ object_name=object_name,
+ element_value=element_value,
+ is_listable=is_listable,
+ xpath=xpath,
+ is_entry=True if object_name == 'nexthop-address-list' else False,
+ is_empty_tag=True if object_name == 'action' else False
+ ),
+ contains_xml_chars=True
+ ),
+ 'action': 'edit',
+ 'type': 'config',
+ 'key': API_KEY
+ }
return http_request(URL, 'POST', params=params)
@@ -13110,7 +13153,8 @@ def pan_os_edit_pbf_rule_command(args):
'description': ('description', 'description', False),
'negate_source': ('negate-source', 'negate-source', False),
'negate_destination': ('negate-destination', 'negate-destination', False),
- 'disabled': ('disabled', 'disabled', False)
+ 'disabled': ('disabled', 'disabled', False),
+ 'audit-comment': ('audit-comment', '', False)
}
if DEVICE_GROUP and not pre_post: # panorama instances must have the pre_post argument!
@@ -13660,6 +13704,49 @@ def pan_os_delete_tag_command(args: dict) -> CommandResults:
)
+def pan_os_get_audit_comment_command(args: dict) -> CommandResults:
+ """
+ executes the command pan-os-get-audit-comment to get the audit comment for a given policy rule.
+
+ Args:
+ args (dict): The command arguments.
+
+ Returns:
+ CommandResults: The command results with raw response, outputs and readable outputs.
+ """
+ if DEVICE_GROUP and not PRE_POST:
+ raise DemistoException(f'The pre_post argument must be provided for panorama instance')
+
+ rule_name = args.get("rule_name") or ""
+ rule_type = args.get("rule_type") or ""
+ params = build_audit_comment_params(
+ name=rule_name,
+ pre_post='rulebase' if VSYS else f'{PRE_POST.lower()}-rulebase',
+ policy_type=RULE_TYPES_MAP[rule_type],
+ xml_type='show',
+ )
+
+ raw_response = http_request(URL, 'GET', params=params)
+ comment = (raw_response["response"]["result"] or {}).get("entry", {}).get("comment", "") or ""
+ outputs = {
+ "rule_name": rule_name,
+ "rule_type": rule_type,
+ "comment": comment
+ }
+
+ return CommandResults(
+ raw_response=raw_response,
+ outputs=outputs,
+ readable_output=tableToMarkdown(
+ f'Audit Comment for Rule: {rule_name}',
+ outputs,
+ headerTransform=string_to_table_header,
+ ),
+ outputs_prefix='Panorama.AuditComment',
+ outputs_key_field=['rule_name', 'rule_type']
+ )
+
+
""" Fetch Incidents """
@@ -14805,6 +14892,8 @@ def main(): # pragma: no cover
return_results(list_device_groups_names())
elif command == 'pan-os-export-tech-support-file':
return_results(export_tsf_command(args))
+ elif command == 'pan-os-get-audit-comment':
+ return_results(pan_os_get_audit_comment_command(args))
else:
raise NotImplementedError(f'Command {command} is not implemented.')
except Exception as err:
diff --git a/Packs/PAN-OS/Integrations/Panorama/Panorama.yml b/Packs/PAN-OS/Integrations/Panorama/Panorama.yml
index 77a4eaa1f716..141cd463e808 100644
--- a/Packs/PAN-OS/Integrations/Panorama/Panorama.yml
+++ b/Packs/PAN-OS/Integrations/Panorama/Panorama.yml
@@ -5148,6 +5148,8 @@ script:
- bottom
- description: The destination rule relative to the rule that you are moving. This field is only relevant if you specify "before" or "after" in the "where" argument.
name: dst
+ - description: An audit comment for the rule.
+ name: audit_comment
description: Creates a policy rule.
execution: true
name: pan-os-create-rule
@@ -8674,6 +8676,8 @@ script:
predefined:
- forward
- reverse
+ - description: An audit comment for the rule.
+ name: audit_comment
description: Creates a new NAT rule in a Panorama/firewall instance.
name: pan-os-create-nat-rule
- arguments:
@@ -8735,6 +8739,7 @@ script:
- destination_translation_dynamic_ip
- destination_translation_dynamic_distribution_method
- disabled
+ - audit-comment
- description: The value of the element to change. Can be a list for certain elements.
isArray: true
name: element_value
@@ -9113,6 +9118,8 @@ script:
- description: The nexthop addresses list for the symmetric return.
isArray: true
name: nexthop_address_list
+ - description: An audit comment for the rule.
+ name: audit_comment
description: Creates a new policy-based-forwarding (PBF) rule in a Panorama/firewall instance.
name: pan-os-create-pbf-rule
- arguments:
@@ -9148,6 +9155,7 @@ script:
- action_forward_discard
- action_forward_no_pbf
- disabled
+ - audit-comment
- description: The value of the element to change. Can be a list for some of the elements. When element_to_change == 'action_forward_egress_interface', the action of the rule will be changed to 'forward' automatically.
isArray: true
name: element_value
@@ -9364,7 +9372,39 @@ script:
description: The job ID to use when polling.
description: Exports a tech support file (TSF).
polling: true
- dockerimage: demisto/pan-os-python:1.0.0.87401
+ - arguments:
+ - description: The rule name to apply.
+ name: rule_name
+ required: true
+ - auto: PREDEFINED
+ description: The rule type.
+ name: rule_type
+ required: true
+ predefined:
+ - Security Rule
+ - NAT Rule
+ - PBF Rule
+ - auto: PREDEFINED
+ description: The pre-rule or post-rule (Panorama instances only).
+ name: pre_post
+ predefined:
+ - Pre
+ - Post
+ - description: The device group that the rule is part of.
+ name: device-group
+ description: Gets the audit comment of a rule.
+ name: pan-os-get-audit-comment
+ outputs:
+ - contextPath: Panorama.AuditComment.comment
+ description: The audit comment ot the rule.
+ type: String
+ - contextPath: Panorama.AuditComment.rule_name
+ description: The rule name.
+ type: String
+ - contextPath: Panorama.AuditComment.rule_type
+ description: The rule type.
+ type: String
+ dockerimage: demisto/pan-os-python:1.0.0.88899
isfetch: true
runonce: false
script: ''
diff --git a/Packs/PAN-OS/Integrations/Panorama/Panorama_test.py b/Packs/PAN-OS/Integrations/Panorama/Panorama_test.py
index c4da35b417e9..2d6afca34e0a 100644
--- a/Packs/PAN-OS/Integrations/Panorama/Panorama_test.py
+++ b/Packs/PAN-OS/Integrations/Panorama/Panorama_test.py
@@ -4272,7 +4272,8 @@ class TestCreatePanOSNatRuleCommand:
'source_translation_type': 'dynamic-ip',
'source_translated_address_type': 'translated-address',
'source_translated_address': '1.1.1.1,2.2.2.2',
- 'destination_translation_type': 'none'
+ 'destination_translation_type': 'none',
+ 'audit_comment': 'test comment',
},
integration_panorama_params,
{
@@ -4284,7 +4285,8 @@ class TestCreatePanOSNatRuleCommand:
'key': 'thisisabogusAPIKEY!',
'type': 'config',
'xpath': "/config/devices/entry[@name='localhost.localdomain']/device-group/entry"
- "[@name='Lab-Devices']/pre-rulebase/nat/rules/entry[@name='test']"
+ "[@name='Lab-Devices']/pre-rulebase/nat/rules/entry[@name='test']",
+ 'audit-comment': 'test comment',
}
),
pytest.param(
@@ -4297,7 +4299,8 @@ class TestCreatePanOSNatRuleCommand:
'source_translation_type': 'dynamic-ip',
'source_translated_address_type': 'translated-address',
'source_translated_address': '1.1.1.1,2.2.2.2',
- 'destination_translation_type': 'none'
+ 'destination_translation_type': 'none',
+ 'audit_comment': 'test comment',
},
integration_firewall_params,
{
@@ -4310,7 +4313,8 @@ class TestCreatePanOSNatRuleCommand:
'key': 'thisisabogusAPIKEY!',
'type': 'config',
'xpath': "/config/devices/entry[@name='localhost.localdomain']/vsys/"
- "entry[@name='vsys1']/rulebase/nat/rules/entry[@name='test']"
+ "entry[@name='vsys1']/rulebase/nat/rules/entry[@name='test']",
+ 'audit-comment': 'test comment',
}
),
]
@@ -4671,6 +4675,52 @@ def test_pan_os_nat_rule_remove_action_main_flow(self, mocker, args, params, exp
assert mock_request.call_args.kwargs['params']['xpath'] == expected_url_params['xpath']
assert mock_request.call_args.kwargs['params'] == expected_url_params
+ @staticmethod
+ def test_pan_os_edit_nat_rule_command_audit_comment_main_flow(mocker):
+ """
+ Given
+ - panorama integrations parameters.
+ - pan-os-edit-nat-rule command arguments including device_group.
+ - arguments to edit audit comment of a rule
+
+ When -
+ running the pan-os-edit-nat-rule command through the main flow
+
+ Then
+ - make sure the context output is returned as expected.
+ - make sure the device group gets overriden by the command arguments.
+ """
+ from Panorama import main
+
+ mocker.patch.object(demisto, 'params', return_value=integration_panorama_params)
+ mocker.patch.object(
+ demisto,
+ 'args',
+ return_value={
+ "rulename": "test",
+ "element_to_change": "audit-comment",
+ "element_value": "some string",
+ "pre_post": "pre-rulebase",
+ "device-group": "new device group"
+ }
+ )
+ mocker.patch.object(demisto, 'command', return_value='pan-os-edit-nat-rule')
+ request_mock = mocker.patch(
+ 'Panorama.http_request', return_value=TestPanoramaEditRuleCommand.EDIT_AUDIT_COMMENT_SUCCESS_RESPONSE
+ )
+
+ res = mocker.patch('demistomock.results')
+ main()
+
+ assert request_mock.call_args.kwargs['params'] == {
+ 'type': 'op',
+ 'cmd': "/config/devices/entry[@name='localhost.localdomain']/device-group"
+ "/entry[@name='new device group']/pre-rulebase/nat/rules/entry[@name='test']"
+ "some string",
+ 'key': 'thisisabogusAPIKEY!'
+ }
+ assert res.call_args.args[0]['Contents'] == TestPanoramaEditRuleCommand.EDIT_AUDIT_COMMENT_SUCCESS_RESPONSE
+
class TestPanOSListVirtualRouters:
@@ -5447,7 +5497,8 @@ class TestCreatePBFRuleCommand:
'nexthop': 'fqdn',
'nexthop_value': '1.1.1.1/24',
'pre_post': 'pre-rulebase',
- 'enforce_symmetric_return': 'yes'
+ 'enforce_symmetric_return': 'yes',
+ 'audit_comment': 'test comment',
},
integration_panorama_params,
{
@@ -5461,7 +5512,8 @@ class TestCreatePBFRuleCommand:
'key': 'thisisabogusAPIKEY!',
'type': 'config',
'xpath': "/config/devices/entry[@name='localhost.localdomain']/device-group/entry"
- "[@name='Lab-Devices']/pre-rulebase/pbf/rules/entry[@name='test']"
+ "[@name='Lab-Devices']/pre-rulebase/pbf/rules/entry[@name='test']",
+ 'audit-comment': 'test comment',
}
),
pytest.param(
@@ -5472,7 +5524,8 @@ class TestCreatePBFRuleCommand:
'egress_interface': 'egress-interface',
'source_zone': 'all access zone external',
'nexthop': 'none',
- 'enforce_symmetric_return': 'no'
+ 'enforce_symmetric_return': 'no',
+ 'audit_comment': 'test comment',
},
integration_firewall_params,
{
@@ -5484,7 +5537,9 @@ class TestCreatePBFRuleCommand:
'key': 'thisisabogusAPIKEY!',
'type': 'config',
'xpath': "/config/devices/entry[@name='localhost.localdomain']/vsys/entry[@name='vsys1']"
- "/rulebase/pbf/rules/entry[@name='test']"}
+ "/rulebase/pbf/rules/entry[@name='test']",
+ 'audit-comment': 'test comment',
+ }
),
]
)
@@ -5769,6 +5824,52 @@ def test_pan_os_edit_pbf_rule_command_remove_action_main_flow(self, mocker, args
main()
assert mock_request.call_args.kwargs['params'] == expected_url_params
+ @staticmethod
+ def test_pan_os_edit_pbf_rule_command_audit_comment_main_flow(mocker):
+ """
+ Given
+ - panorama integrations parameters.
+ - pan-os-edit-pbf-rule command arguments including device_group.
+ - arguments to edit audit comment of a rule
+
+ When -
+ running the pan-os-edit-pbf-rule command through the main flow
+
+ Then
+ - make sure the context output is returned as expected.
+ - make sure the device group gets overriden by the command arguments.
+ """
+ from Panorama import main
+
+ mocker.patch.object(demisto, 'params', return_value=integration_panorama_params)
+ mocker.patch.object(
+ demisto,
+ 'args',
+ return_value={
+ "rulename": "test",
+ "element_to_change": "audit-comment",
+ "element_value": "some string",
+ "pre_post": "pre-rulebase",
+ "device-group": "new device group"
+ }
+ )
+ mocker.patch.object(demisto, 'command', return_value='pan-os-edit-pbf-rule')
+ request_mock = mocker.patch(
+ 'Panorama.http_request', return_value=TestPanoramaEditRuleCommand.EDIT_AUDIT_COMMENT_SUCCESS_RESPONSE
+ )
+
+ res = mocker.patch('demistomock.results')
+ main()
+
+ assert request_mock.call_args.kwargs['params'] == {
+ 'type': 'op',
+ 'cmd': "/config/devices/entry[@name='localhost.localdomain']/device-group"
+ "/entry[@name='new device group']/pre-rulebase/pbf/rules/entry[@name='test']"
+ "some string",
+ 'key': 'thisisabogusAPIKEY!'
+ }
+ assert res.call_args.args[0]['Contents'] == TestPanoramaEditRuleCommand.EDIT_AUDIT_COMMENT_SUCCESS_RESPONSE
+
@pytest.mark.parametrize(
'args, params, expected_url_params',
diff --git a/Packs/PAN-OS/Integrations/Panorama/README.md b/Packs/PAN-OS/Integrations/Panorama/README.md
index a15582efcaf7..f79fc7532bf7 100644
--- a/Packs/PAN-OS/Integrations/Panorama/README.md
+++ b/Packs/PAN-OS/Integrations/Panorama/README.md
@@ -2328,6 +2328,7 @@ Creates a policy rule.
| profile_setting | A profile setting group. | Optional |
| where | Where to move the rule. Can be "before", "after", "top", or "bottom". If you specify "before" or "after", you need to supply the "dst" argument. | Optional |
| dst | Destination rule relative to the rule that you are moving. This field is only relevant if you specify "before" or "after" in the "where" argument. | Optional |
+| audit_comment | An audit comment for the rule. | Optional |
#### Context Output
@@ -7958,6 +7959,7 @@ Creates a new NAT rule in a Panorama/firewall instance.
| destination_translation_distribution_method | The destination translation distribution method. Possible values are: round-robin, source-ip-hash, ip-modulo, ip-hash, least-sessions. | Optional |
| negate_destination | Whether to use negate destination. Possible values are: yes, no. | Optional |
| destination_dns_rewrite_direction | The DNS rewrite direction. Possible values are: forward, reverse. | Optional |
+| audit_comment | An audit comment for the rule. | Optional |
#### Context Output
@@ -8007,7 +8009,7 @@ Edits a NAT rule.
| device-group | The device-group that the NAT rule is part of. (Panorama instances only). | Optional |
| pre_post | The pre rule or post rule (Panorama instances only). Possible values are: pre-rulebase, post-rulebase. | Optional |
| behavior | The operation to perform on the rule. Possible values are: replace, add, remove. Default is replace. | Optional |
-| element_to_change | The element to change. Possible values are: tags, service, nat_type, description, source_zone, destination_zone, source_address, destination_address, destination_interface, negate_destination, source_translation_dynamic_ip_and_port, source_translation_interface, source_translation_dynamic_ip, source_translation_static_ip, destination_translation_port, destination_translation_ip, destination_translation_dynamic_port, destination_translation_dynamic_ip, destination_translation_dynamic_distribution_method, disabled. | Required |
+| element_to_change | The element to change. Possible values are: tags, service, nat_type, description, source_zone, destination_zone, source_address, destination_address, destination_interface, negate_destination, source_translation_dynamic_ip_and_port, source_translation_interface, source_translation_dynamic_ip, source_translation_static_ip, destination_translation_port, destination_translation_ip, destination_translation_dynamic_port, destination_translation_dynamic_ip, destination_translation_dynamic_distribution_method, disabled, audit-comment. | Required |
| element_value | The value of the element to change. Can be a list for certain elements. | Required |
@@ -8573,6 +8575,7 @@ Creates a new policy-based-forwarding (PBF) rule in a Panorama/firewall instance
| negate_source | Whether to negate the source. Possible values are: yes, no. Default is no. | Optional |
| negate_destination | Whether to negate the destination. Possible values are: yes, no. Default is no. | Optional |
| nexthop_address_list | The nexthop addresses list for the symmetric return. | Optional |
+| audit_comment | An audit comment for the rule. | Optional |
#### Context Output
@@ -8598,7 +8601,7 @@ Edits a redistribution-profile in a virtual-router.
| rulename | The name of the PBF rule to edit. Can be retrieved from the pan-os-list-pbf-rules command. | Required |
| device-group | The device-group that the PBF rule is in. | Optional |
| pre_post | The pre-rule or post-rule (Panorama instances only). Possible values are: pre-rulebase, post-rulebase. | Optional |
-| element_to_change | The element to change. Possible values are: source_zone, source_address, source_user, service, destination_address, application, negate_source, negate_destination, nexthop_address_list, enforce_symmetric_return, action_forward_egress_interface, action_forward_nexthop_ip, action_forward_nexthop_fqdn, action_forward_discard, action_forward_no_pbf, disabled. | Required |
+| element_to_change | The element to change. Possible values are: source_zone, source_address, source_user, service, destination_address, application, negate_source, negate_destination, nexthop_address_list, enforce_symmetric_return, action_forward_egress_interface, action_forward_nexthop_ip, action_forward_nexthop_fqdn, action_forward_discard, action_forward_no_pbf, disabled, audit-comment. | Required |
| element_value | The value of the element to change. Can be a list for some of the elements. When element_to_change == 'action_forward_egress_interface', the action of the rule will be changed to 'forward' automatically. | Required |
@@ -9014,3 +9017,46 @@ There is no context output for this command.
#### Human Readable Output
>Waiting for tech support file export with job ID 101 to finish...
+
+### pan-os-get-audit-comment
+
+***
+Gets the audit comment of a rule.
+
+#### Base Command
+
+`pan-os-get-audit-comment`
+
+#### Input
+
+| **Argument Name** | **Description** | **Required** |
+| --- | --- | --- |
+| rule_name | The rule name to apply. | Required |
+| rule_type | The rule type. Possible values are: Security Rule, NAT Rule, PBF Rule. | Optional |
+| pre_post | Pre rule or Post rule (Panorama instances). | Optional |
+| device_group | The device group that the tag will be part of. | Optional |
+
+#### Command example
+```!pan-os-get-audit-comment rule_name="test" rule_type="Security Rule" pre_post=Post```
+
+#### Context Example
+```json
+{
+ "Panorama": {
+ "AuditComment": [
+ {
+ "comment": "some comment",
+ "rule_name": "test",
+ "rule_type": "Security Rule"
+ }
+ ]
+ }
+}
+```
+
+#### Human Readable Output
+
+>### Audit Comment for Rule: test
+>|Comment|Rule Name|Rule Type|
+>|---|---|---|
+>| some comment | test | Security Rule |
diff --git a/Packs/PAN-OS/ReleaseNotes/2_1_23.md b/Packs/PAN-OS/ReleaseNotes/2_1_23.md
new file mode 100644
index 000000000000..212c98ac738b
--- /dev/null
+++ b/Packs/PAN-OS/ReleaseNotes/2_1_23.md
@@ -0,0 +1,15 @@
+
+#### Integrations
+
+##### Palo Alto Networks PAN-OS
+
+- Added a new command ***pan-os-get-audit-comment***.
+- Added the *audit-comment* argument to the following commands:
+ - ***pan-os-create-rule***
+ - ***pan-os-create-pbf-rule***
+ - ***pan-os-create-nat-rule***
+- Added the new option *audit-comment* to the *element_to_change* argument in the following commands:
+ - ***pan-os-edit-pbf-rule***
+ - ***pan-os-edit-nat-rule***
+- Added the *ip-wildcard* data to the ***pan-os-list-addresses*** outputs.
+- Updated the Docker image to: *demisto/pan-os-python:1.0.0.88899*.
diff --git a/Packs/PAN-OS/pack_metadata.json b/Packs/PAN-OS/pack_metadata.json
index 30c11b50680a..24c250bf86cc 100644
--- a/Packs/PAN-OS/pack_metadata.json
+++ b/Packs/PAN-OS/pack_metadata.json
@@ -2,7 +2,7 @@
"name": "PAN-OS by Palo Alto Networks",
"description": "Manage Palo Alto Networks Firewall and Panorama. Use this pack to manage Prisma Access through Panorama. For more information see Panorama documentation.",
"support": "xsoar",
- "currentVersion": "2.1.22",
+ "currentVersion": "2.1.23",
"author": "Cortex XSOAR",
"url": "https://www.paloaltonetworks.com/cortex",
"email": "",
diff --git a/Packs/ServiceNow/.pack-ignore b/Packs/ServiceNow/.pack-ignore
index 061a73da6e67..a8814557754c 100644
--- a/Packs/ServiceNow/.pack-ignore
+++ b/Packs/ServiceNow/.pack-ignore
@@ -45,10 +45,10 @@ cmdb
bypassaddrecord
closereason
closenotes
+mmm
[file:classifier-ServiceNow.json]
ignore=BA101
[file:ServiceNowIncidentStatus.yml]
-ignore=BA124
-
+ignore=BA124
\ No newline at end of file
diff --git a/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2.py b/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2.py
index 2afaa2848362..7fd7db338f83 100644
--- a/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2.py
+++ b/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2.py
@@ -25,7 +25,8 @@
'dd/MM/yyyy': '%d/%m/%Y %H:%M:%S',
'dd-MM-yyyy': '%d-%m-%Y %H:%M:%S',
'dd.MM.yyyy': '%d.%m.%Y %H:%M:%S',
- 'yyyy-MM-dd': '%Y-%m-%d %H:%M:%S'
+ 'yyyy-MM-dd': '%Y-%m-%d %H:%M:%S',
+ 'mmm-dd-yyyy': '%b-%d-%Y %H:%M:%S'
}
TICKET_STATES = {
diff --git a/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2.yml b/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2.yml
index a65ad3cab927..bf2dac5baed6 100644
--- a/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2.yml
+++ b/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2.yml
@@ -94,6 +94,7 @@ configuration:
- dd-MM-yyyy
- dd.MM.yyyy
- yyyy-MM-dd
+ - mmm-dd-yyyy
type: 15
required: false
- additionalinfo: Choose the tag to add to an entry to mirror it as a comment in ServiceNow.
diff --git a/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2_test.py b/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2_test.py
index b10bddc8a785..72a4dccab9da 100644
--- a/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2_test.py
+++ b/Packs/ServiceNow/Integrations/ServiceNowv2/ServiceNowv2_test.py
@@ -329,6 +329,11 @@ def test_get_timezone_offset():
offset = get_timezone_offset(full_response, display_date_format=DATE_FORMAT_OPTIONS.get('dd.MM.yyyy'))
assert offset == timedelta(minutes=-300)
+ full_response = {
+ 'result': {'sys_created_on': {'display_value': 'Dec-07-2022 00:38:52', 'value': '2022-12-06 19:38:52'}}}
+ offset = get_timezone_offset(full_response, display_date_format=DATE_FORMAT_OPTIONS.get('mmm-dd-yyyy'))
+ assert offset == timedelta(minutes=-300)
+
@pytest.mark.parametrize('command, args, response, expected_result, expected_auto_extract', [
(update_ticket_command, {'id': '1234', 'impact': '2'}, RESPONSE_UPDATE_TICKET, EXPECTED_UPDATE_TICKET, True),
diff --git a/Packs/ServiceNow/ReleaseNotes/2_5_57.md b/Packs/ServiceNow/ReleaseNotes/2_5_57.md
new file mode 100644
index 000000000000..e3ef54383e31
--- /dev/null
+++ b/Packs/ServiceNow/ReleaseNotes/2_5_57.md
@@ -0,0 +1,5 @@
+#### Integrations
+
+##### ServiceNow v2
+
+Added support for a new time format: mmm-dd-yyyy i.e., Dec-07-2022 00:38:52.
diff --git a/Packs/ServiceNow/pack_metadata.json b/Packs/ServiceNow/pack_metadata.json
index 388bfda2afb2..1b071a1eca92 100644
--- a/Packs/ServiceNow/pack_metadata.json
+++ b/Packs/ServiceNow/pack_metadata.json
@@ -2,7 +2,7 @@
"name": "ServiceNow",
"description": "Use The ServiceNow IT Service Management (ITSM) solution to modernize the way you manage and deliver services to your users.",
"support": "xsoar",
- "currentVersion": "2.5.56",
+ "currentVersion": "2.5.57",
"author": "Cortex XSOAR",
"url": "https://www.paloaltonetworks.com/cortex",
"email": "",