Skip to content

Commit 41b5b24

Browse files
committedJan 13, 2023
Add context and fix bandit and semgrep findings
Signed-off-by: Francesco Giordano <[email protected]>
1 parent 2abbac5 commit 41b5b24

File tree

21 files changed

+85
-54
lines changed

21 files changed

+85
-54
lines changed
 

‎awsbatch-cli/src/awsbatch/awsbhosts.py

+4-4
Original file line numberDiff line numberDiff line change
@@ -284,13 +284,13 @@ def __get_ecs_clusters(self, compute_environments):
284284
try:
285285
# connect to batch and ask for compute environments
286286
batch_client = self.boto3_factory.get_client("batch")
287-
next_token = "" # nosec
288-
while next_token is not None:
287+
next_page = ""
288+
while next_page is not None:
289289
response = batch_client.describe_compute_environments(
290-
computeEnvironments=compute_environments, nextToken=next_token
290+
computeEnvironments=compute_environments, nextToken=next_page
291291
)
292292
ecs_clusters.extend(self.__get_clusters(response["computeEnvironments"]))
293-
next_token = response.get("nextToken")
293+
next_page = response.get("nextToken")
294294
except Exception as e:
295295
fail("Error listing compute environments from AWS Batch. Failed with exception: %s" % e)
296296

‎awsbatch-cli/src/awsbatch/awsbstat.py

+4-4
Original file line numberDiff line numberDiff line change
@@ -461,16 +461,16 @@ def __populate_output_by_queue(self, job_queue, job_status, expand_children, det
461461
single_jobs = []
462462
jobs_with_children = []
463463
for status in job_status:
464-
next_token = "" # nosec
465-
while next_token is not None:
466-
response = self.batch_client.list_jobs(jobStatus=status, jobQueue=job_queue, nextToken=next_token)
464+
next_page = ""
465+
while next_page is not None:
466+
response = self.batch_client.list_jobs(jobStatus=status, jobQueue=job_queue, nextToken=next_page)
467467

468468
for job in response["jobSummaryList"]:
469469
if get_job_type(job) != "SIMPLE" and expand_children is True:
470470
jobs_with_children.append(job["jobId"])
471471
else:
472472
single_jobs.append(job)
473-
next_token = response.get("nextToken")
473+
next_page = response.get("nextToken")
474474

475475
# create output items for job array children
476476
self.__populate_output_by_job_ids(jobs_with_children, details)

‎cli/src/pcluster/api/controllers/cluster_compute_fleet_controller.py

+5-2
Original file line numberDiff line numberDiff line change
@@ -80,8 +80,11 @@ def update_compute_fleet(update_compute_fleet_request_content, cluster_name, reg
8080
elif status == RequestedComputeFleetStatus.STOP_REQUESTED:
8181
cluster.stop()
8282
else:
83-
raise BadRequestException( # nosec
84-
"the update compute fleet status can only be set to"
83+
# A nosec comment is appended to the following line in order to disable the false positive B608 check.
84+
# False positive since it is not a SQL query.
85+
# [B608:hardcoded_sql_expressions] Possible SQL injection vector through string-based query construction.
86+
raise BadRequestException(
87+
"the update compute fleet status can only be set to" # nosec B608
8588
" `START_REQUESTED` or `STOP_REQUESTED` for %s scheduler clusters."
8689
% cluster.stack.scheduler.capitalize()
8790
)

‎cli/src/pcluster/api/util.py

+4-2
Original file line numberDiff line numberDiff line change
@@ -180,23 +180,25 @@ def _assert_node_executable():
180180
def _assert_node_version():
181181
try:
182182
# A nosec comment is appended to the following line in order to disable the B607 and B603 checks.
183+
# It is a false positive since the PATH search is wanted and the input of the check_output is static.
183184
# [B607:start_process_with_partial_path] Is suppressed because location of executable is retrieved from env
184185
# PATH
185186
# [B603:subprocess_without_shell_equals_true] Is suppressed because input of check_output is not coming from
186187
# untrusted source
187-
node_version_string = subprocess.check_output( # nosec
188+
node_version_string = subprocess.check_output( # nosec B607 B603
188189
["node", "--version"], stderr=subprocess.STDOUT, shell=False, encoding="utf-8"
189190
)
190191
LOGGER.debug("Found Node.js version (%s)", node_version_string)
191192
except Exception:
192193
LOGGER.debug("Unable to determine current Node.js version from node")
193194
try:
194195
# A nosec comment is appended to the following line in order to disable the B607 and B603 checks.
196+
# It is a false positive since the PATH search is wanted and the input of the check_output is static.
195197
# [B607:start_process_with_partial_path] Is suppressed because location of executable is retrieved from env
196198
# PATH
197199
# [B603:subprocess_without_shell_equals_true] Is suppressed because input of check_output is not coming from
198200
# untrusted source
199-
node_version_string = subprocess.check_output( # nosec
201+
node_version_string = subprocess.check_output( # nosec B607 B603
200202
["nvm", "current"], stderr=subprocess.STDOUT, shell=False, encoding="utf-8"
201203
)
202204
LOGGER.debug("Found Node.js version '%s' in use", node_version_string)

‎cli/src/pcluster/cli/commands/dcv_connect.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -38,8 +38,8 @@ class DCVConnectionError(Exception):
3838
def _check_command_output(cmd):
3939
# A nosec comment is appended to the following line in order to disable the B602 check.
4040
# This is done because it's needed to enable the desired functionality. The only caller
41-
# of this function is _retrieve_dcv_session_url, which passes a command that should be safe.
42-
return sub.check_output(cmd, shell=True, universal_newlines=True, stderr=sub.STDOUT).strip() # nosec nosemgrep
41+
# of this function is _retrieve_dcv_session_url, which passes a command that is safe.
42+
return sub.check_output(cmd, shell=True, universal_newlines=True, stderr=sub.STDOUT).strip() # nosec B602 nosemgrep
4343

4444

4545
def _dcv_connect(args):

‎cli/src/pcluster/cli/commands/ssh.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -64,7 +64,7 @@ def _ssh(args, extra_args):
6464
# - The args passed to the remote command are sanitized.
6565
# - The default command to which these args is known.
6666
# - Users have full control over any customization of the command to which args are passed.
67-
os.system(cmd) # nosec nosemgrep
67+
os.system(cmd) # nosec B605 nosemgrep
6868
else:
6969
print(json.dumps({"command": cmd}, indent=2))
7070

‎cli/src/pcluster/models/cluster.py

+10-4
Original file line numberDiff line numberDiff line change
@@ -570,9 +570,10 @@ def _render_and_upload_scheduler_plugin_template(self, dry_run=False):
570570
)
571571
file_content = result["Body"].read().decode("utf-8")
572572
else:
573-
with urlopen( # nosec nosemgrep - scheduler_plugin_template url is properly validated
574-
scheduler_plugin_template
575-
) as f:
573+
# A nosec comment is appended to the following line in order to disable the B310 check.
574+
# The urlopen argument is properly validated
575+
# [B310:blacklist] Audit url open for permitted schemes.
576+
with urlopen(scheduler_plugin_template) as f: # nosec B310 nosemgrep
576577
file_content = f.read().decode("utf-8")
577578
except Exception as e:
578579
raise BadRequestClusterActionError(
@@ -587,7 +588,12 @@ def _render_and_upload_scheduler_plugin_template(self, dry_run=False):
587588
LOGGER.info("Rendering the following scheduler plugin CloudFormation template:\n%s", file_content)
588589
environment = SandboxedEnvironment(loader=BaseLoader)
589590
environment.filters["hash"] = (
590-
lambda value: hashlib.sha1(value.encode()).hexdigest()[0:16].capitalize() # nosec nosemgrep
591+
# A nosec comment is appended to the following line in order to disable the B324 checks.
592+
# The sha1 is used just as a hashing function.
593+
# [B324:hashlib] Use of weak MD4, MD5, or SHA1 hash for security. Consider usedforsecurity=False
594+
lambda value: hashlib.sha1(value.encode()) # nosec B324 nosemgrep
595+
.hexdigest()[0:16]
596+
.capitalize()
591597
)
592598
template = environment.from_string(file_content)
593599
rendered_template = template.render(

‎cli/src/pcluster/resources/custom_resources/custom_resources_code/crhelper/resource_helper.py

+4-1
Original file line numberDiff line numberDiff line change
@@ -261,7 +261,10 @@ def _cleanup_response(self):
261261

262262
@staticmethod
263263
def _rand_string(length):
264-
return ''.join(random.choice(string.ascii_uppercase + string.digits) for _ in range(length)) # nosec
264+
# A nosec comment is appended to the following line in order to disable the B311 check.
265+
# The random.choice is used to generate random string for names.
266+
# [B311:blacklist] Standard pseudo-random generators are not suitable for security/cryptographic purposes.
267+
return ''.join(random.choice(string.ascii_uppercase + string.digits) for _ in range(length)) # nosec B311
265268

266269
def _add_permission(self, rule_arn):
267270
sid = self._event['LogicalResourceId'] + self._rand_string(8)

‎cli/src/pcluster/resources/custom_resources/custom_resources_code/crhelper/utils.py

+4-1
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,10 @@ def _send_response(response_url, response_body):
2727
url = urlunsplit(("", "", *split_url[2:]))
2828
while True:
2929
try:
30-
connection = HTTPSConnection(host) # nosec nosemgrep
30+
# A nosec comment is appended to the following line in order to disable the B309 check.
31+
# ParallelCluster only supports python >= 3.4.3
32+
# [B309:blacklist] Use of HTTPSConnection on older versions of Python prior to 2.7.9 and 3.4.3 do not provide security, see https://wiki.openstack.org/wiki/OSSN/OSSN-0033
33+
connection = HTTPSConnection(host) # nosec B309 nosemgrep
3134
connection.request(method="PUT", url=url, body=json_response_body, headers=headers)
3235
response = connection.getresponse()
3336
logger.info("CloudFormation returned status code: %s", response.reason)

‎cli/src/pcluster/resources/custom_resources/custom_resources_code/send_build_notification.py

+5-1
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,11 @@ def handler(event, context): # pylint: disable=unused-argument
3838
url = urlunsplit(("", "", *split_url[2:]))
3939
while True:
4040
try:
41-
connection = HTTPSConnection(host) # nosec nosemgrep
41+
# A nosec comment is appended to the following line in order to disable the B309 check.
42+
# ParallelCluster only supports python >= 3.4.3
43+
# [B309:blacklist] Use of HTTPSConnection on older versions of Python prior to 2.7.9 and 3.4.3
44+
# do not provide security, see https://wiki.openstack.org/wiki/OSSN/OSSN-0033
45+
connection = HTTPSConnection(host) # nosec B309 nosemgrep
4246
connection.request(
4347
method="PUT", url=url, body=data, headers={"Content-Type": "", "content-length": str(len(data))}
4448
)

‎cli/src/pcluster/schemas/cluster_schema.py

+4-1
Original file line numberDiff line numberDiff line change
@@ -1764,7 +1764,10 @@ def _fetch_scheduler_definition_from_s3(self, original_scheduler_definition, s3_
17641764

17651765
def _fetch_scheduler_definition_from_https(self, original_scheduler_definition):
17661766
try:
1767-
with urlopen(original_scheduler_definition) as f: # nosec nosemgrep
1767+
# A nosec comment is appended to the following line in order to disable the B310 check.
1768+
# The urlopen argument is properly validated
1769+
# [B310:blacklist] Audit url open for permitted schemes.
1770+
with urlopen(original_scheduler_definition) as f: # nosec B310 nosemgrep
17681771
scheduler_definition = f.read().decode("utf-8")
17691772
return scheduler_definition
17701773
except Exception:

‎cli/src/pcluster/templates/cdk_builder_utils.py

+8-2
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,10 @@ def create_hash_suffix(string_to_hash: str):
5858
return (
5959
string_to_hash
6060
if string_to_hash == "HeadNode"
61-
else sha1(string_to_hash.encode("utf-8")).hexdigest()[:16].capitalize() # nosec nosemgrep
61+
# A nosec comment is appended to the following line in order to disable the B324 check.
62+
# The sha1 is used just as a hashing function.
63+
# [B324:hashlib] Use of weak MD4, MD5, or SHA1 hash for security. Consider usedforsecurity=False
64+
else sha1(string_to_hash.encode("utf-8")).hexdigest()[:16].capitalize() # nosec B324 nosemgrep
6265
)
6366

6467

@@ -315,7 +318,10 @@ def generate_launch_template_version_cfn_parameter_hash(queue, compute_resource)
315318
:param compute_resource
316319
:return: 16 chars string e.g. 2238a84ac8a74529
317320
"""
318-
return hashlib.sha1((queue + compute_resource).encode()).hexdigest()[0:16].capitalize() # nosec nosemgrep
321+
# A nosec comment is appended to the following line in order to disable the B324 check.
322+
# The sha1 is used just as a hashing function.
323+
# [B324:hashlib] Use of weak MD4, MD5, or SHA1 hash for security. Consider usedforsecurity=False
324+
return hashlib.sha1((queue + compute_resource).encode()).hexdigest()[0:16].capitalize() # nosec B324 nosemgrep
319325

320326

321327
class NodeIamResourcesBase(Construct):

‎cli/src/pcluster/templates/cluster_stack.py

+12-3
Original file line numberDiff line numberDiff line change
@@ -1074,7 +1074,10 @@ def _add_head_node(self):
10741074
},
10751075
"deployConfigFiles": {
10761076
"files": {
1077-
"/tmp/dna.json": { # nosec
1077+
# A nosec comment is appended to the following line in order to disable the B108 check.
1078+
# The file is needed by the product
1079+
# [B108:hardcoded_tmp_directory] Probable insecure usage of temp file/directory.
1080+
"/tmp/dna.json": { # nosec B108
10781081
"content": dna_json,
10791082
"mode": "000644",
10801083
"owner": "root",
@@ -1087,13 +1090,19 @@ def _add_head_node(self):
10871090
"group": "root",
10881091
"content": "cookbook_path ['/etc/chef/cookbooks']",
10891092
},
1090-
"/tmp/extra.json": { # nosec
1093+
# A nosec comment is appended to the following line in order to disable the B108 check.
1094+
# The file is needed by the product
1095+
# [B108:hardcoded_tmp_directory] Probable insecure usage of temp file/directory.
1096+
"/tmp/extra.json": { # nosec B108
10911097
"mode": "000644",
10921098
"owner": "root",
10931099
"group": "root",
10941100
"content": self.config.extra_chef_attributes,
10951101
},
1096-
"/tmp/wait_condition_handle.txt": { # nosec
1102+
# A nosec comment is appended to the following line in order to disable the B108 check.
1103+
# The file is needed by the product
1104+
# [B108:hardcoded_tmp_directory] Probable insecure usage of temp file/directory.
1105+
"/tmp/wait_condition_handle.txt": { # nosec B108
10971106
"mode": "000644",
10981107
"owner": "root",
10991108
"group": "root",

‎cli/src/pcluster/utils.py

+5-16
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,6 @@
1818
import string
1919
import sys
2020
import time
21-
import urllib.request
2221
import zipfile
2322
from io import BytesIO
2423
from shlex import quote
@@ -28,7 +27,6 @@
2827
import dateutil.parser
2928
import pkg_resources
3029
import yaml
31-
from pkg_resources import packaging
3230
from yaml import SafeLoader
3331
from yaml.constructor import ConstructorError
3432
from yaml.resolver import BaseResolver
@@ -64,7 +62,7 @@ def generate_random_name_with_prefix(name_prefix):
6462
Example: <name_prefix>-4htvo26lchkqeho1
6563
"""
6664
random_string = generate_random_prefix()
67-
output_name = "-".join([name_prefix.lower()[: 63 - len(random_string) - 1], random_string]) # nosec
65+
output_name = "-".join([name_prefix.lower()[: 63 - len(random_string) - 1], random_string])
6866
return output_name
6967

7068

@@ -74,7 +72,10 @@ def generate_random_prefix():
7472
7573
Example: 4htvo26lchkqeho1
7674
"""
77-
return "".join(random.choice(string.ascii_lowercase + string.digits) for _ in range(16)) # nosec
75+
# A nosec comment is appended to the following line in order to disable the B311 check.
76+
# The random.choice is used to generate random string for names.
77+
# [B311:blacklist] Standard pseudo-random generators are not suitable for security/cryptographic purposes.
78+
return "".join(random.choice(string.ascii_lowercase + string.digits) for _ in range(16)) # nosec B311
7879

7980

8081
def _add_file_to_zip(zip_file, path, arcname):
@@ -251,18 +252,6 @@ def get_installed_version(base_version_only: bool = False):
251252
return pkg_distribution.version if not base_version_only else pkg_distribution.parsed_version.base_version
252253

253254

254-
def check_if_latest_version():
255-
"""Check if the current package version is the latest one."""
256-
try:
257-
pypi_url = "https://pypi.python.org/pypi/aws-parallelcluster/json"
258-
with urllib.request.urlopen(pypi_url) as url: # nosec nosemgrep
259-
latest = json.loads(url.read())["info"]["version"]
260-
if packaging.version.parse(get_installed_version()) < packaging.version.parse(latest):
261-
print(f"Info: There is a newer version {latest} of AWS ParallelCluster available.")
262-
except Exception: # nosec
263-
pass
264-
265-
266255
def warn(message):
267256
"""Print a warning message."""
268257
print(f"WARNING: {message}")

‎cli/src/pcluster/validators/cluster_validators.py

+4-1
Original file line numberDiff line numberDiff line change
@@ -878,7 +878,10 @@ def _validate(self, mount_dir: str):
878878
"/sbin",
879879
"/srv",
880880
"/sys",
881-
"/tmp", # nosec nosemgrep
881+
# A nosec comment is appended to the following line in order to disable the B108 check.
882+
# It is a false positive since is a list to check folder name
883+
# [B108:hardcoded_tmp_directory] Probable insecure usage of temp file/directory.
884+
"/tmp", # nosec B108
882885
"/usr",
883886
"/var",
884887
]

‎cli/src/pcluster/validators/s3_validators.py

+4-1
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,10 @@ def _validate_s3_uri(self, url: str, fail_on_error: bool, expected_bucket_owner:
6868

6969
def _validate_https_uri(self, url: str, fail_on_error: bool):
7070
try:
71-
with urlopen(url): # nosec nosemgrep
71+
# A nosec comment is appended to the following line in order to disable the B310 check.
72+
# The urlopen argument is properly validated
73+
# [B310:blacklist] Audit url open for permitted schemes.
74+
with urlopen(url): # nosec B310 nosemgrep
7275
pass
7376
except HTTPError as e:
7477
self._add_failure(

‎scheduler_plugins/slurm/artifacts/slurm_plugin_cookbook/files/default/head_node_slurm/slurm/pcluster_slurm_config_generator.py

+1-4
Original file line numberDiff line numberDiff line change
@@ -145,10 +145,7 @@ def _generate_slurm_parallelcluster_configs(
145145
def _get_jinja_env(template_directory):
146146
"""Return jinja environment with trim_blocks/lstrip_blocks set to True."""
147147
file_loader = FileSystemLoader(template_directory)
148-
# A nosec comment is appended to the following line in order to disable the B701 check.
149-
# The contents of the default templates are known and the input configuration data is
150-
# validated by the CLI.
151-
env = SandboxedEnvironment(loader=file_loader, trim_blocks=True, lstrip_blocks=True) # nosec nosemgrep
148+
env = SandboxedEnvironment(loader=file_loader, trim_blocks=True, lstrip_blocks=True)
152149
env.filters["sanify_name"] = lambda value: re.sub(r"[^A-Za-z0-9]", "", value)
153150
env.filters["gpus"] = _gpu_count
154151
env.filters["gpu_type"] = _gpu_type

‎scheduler_plugins/slurm/artifacts/slurm_plugin_cookbook/recipes/install_slurm.rb

+1-1
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@
4848
ruby_block 'Validate Slurm Tarball Checksum' do
4949
block do
5050
require 'digest'
51-
checksum = Digest::SHA1.file(slurm_tarball).hexdigest # nosemgrep
51+
checksum = Digest::SHA1.file(slurm_tarball).hexdigest
5252
raise "Downloaded Tarball Checksum #{checksum} does not match expected checksum #{node['slurm']['sha1']}" if checksum != node['slurm']['sha1']
5353
end
5454
end

‎util/sync_buckets.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -125,7 +125,7 @@ def _aws_credentials_type(value):
125125

126126
def _get_s3_object_metadata(s3_url):
127127
req = urllib.request.Request(url=s3_url, method="HEAD")
128-
response = urllib.request.urlopen(req) # nosec nosemgrep
128+
response = urllib.request.urlopen(req) # nosec
129129
assert response.status == 200 # nosec
130130
metadata = {}
131131
metadata["version_id"] = response.headers.get("x-amz-version-id")

‎util/update_pcluster_configs.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -294,7 +294,7 @@ def _get_batch_instance_whitelist(region, credentials):
294294

295295

296296
def _read_json_from_url(url):
297-
response = urlopen(url) # nosec nosemgrep
297+
response = urlopen(url) # nosec
298298
return json.loads(response.read().decode("utf-8"))
299299

300300

‎util/upload-cookbook.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -134,7 +134,7 @@ def _get_bucket_name(args, region):
134134

135135
def _md5sum(cookbook_archive_file, md5sum_file):
136136
blocksize = 65536
137-
hasher = hashlib.md5() # nosec nosemgrep
137+
hasher = hashlib.md5() # nosec
138138
with open(cookbook_archive_file, "rb") as arch:
139139
buf = arch.read(blocksize)
140140
while len(buf) > 0:

0 commit comments

Comments
 (0)
Please sign in to comment.