Secure your code as it's written. Use Snyk Code to scan source code in minutes - no build needed - and fix issues immediately.
def get_commands_from_history(image_layer):
'''Given the image layer object and the shell, get the list of command
objects that created the layer'''
# set up notice origin for the layer
origin_layer = 'Layer: ' + image_layer.fs_hash[:10]
if image_layer.created_by:
instruction = created_to_instruction(image_layer.created_by)
image_layer.origins.add_notice_to_origins(origin_layer, Notice(
formats.dockerfile_line.format(dockerfile_instruction=instruction),
'info'))
else:
image_layer.origins.add_notice_to_origins(origin_layer, Notice(
formats.no_created_by, 'warning'))
command_line = instruction.split(' ', 1)[1]
# Image layers are created with the directives RUN, ADD and COPY
# For ADD and COPY instructions, there is no information about the
# packages added
if 'ADD' in instruction or 'COPY' in instruction:
image_layer.origins.add_notice_to_origins(origin_layer, Notice(
errors.unknown_content.format(files=command_line), 'warning'))
# return an empty list as we cannot find any commands
return []
# for RUN instructions we can return a list of commands
command_list, msg = common.filter_install_commands(command_line)
if msg:
'''Execution path if given a Docker image'''
logger.debug('Setting up...')
image_string = args.docker_image
if not args.raw_image:
# don't check docker daemon for raw images
container.check_docker_setup()
else:
image_string = args.raw_image
report.setup(image_tag_string=image_string)
# attempt to get built image metadata
full_image = report.load_full_image(image_string)
if full_image.origins.is_empty():
# image loading was successful
# Add an image origin here
full_image.origins.add_notice_origin(
formats.docker_image.format(imagetag=image_string))
# analyze image
analyze(full_image, args)
# generate report
report.report_out(args, full_image)
else:
# we cannot load the full image
logger.warning('Cannot retrieve full image metadata')
if not args.keep_wd:
report.clean_image_tars(full_image)
logger.debug('Teardown...')
report.teardown()
if not args.keep_wd:
report.clean_working_dir()
def generate_verbose(is_summary, images):
'''Generate a verbose report'''
report = formats.disclaimer.format(
version_info=content.get_tool_version())
if is_summary:
logger.debug('Creating a summary of components in image...')
for image in images:
report = report + content.print_summary_report(image)
else:
logger.debug('Creating a detailed report of components in image...')
for image in images:
report = report + content.print_full_report(image)
return report
for layer_origin in layer.origins.origins:
notes = notes + content.print_notices(layer_origin,
'\t', '\t\t')
layer_pkg_list = []
layer_license_list = []
for package in layer.packages:
pkg = package.name + "-" + package.version
if pkg not in layer_pkg_list and pkg:
layer_pkg_list.append(pkg)
if package.pkg_license not in layer_license_list and \
package.pkg_license:
layer_license_list.append(package.pkg_license)
# Collect packages + licenses in the layer
notes = notes + formats.layer_packages_list.format(
list=", ".join(layer_pkg_list) if layer_pkg_list else 'None')
notes = notes + formats.layer_licenses_list.format(list=", ".join(
layer_license_list) if layer_license_list else 'None')
notes = notes + formats.package_demarkation
return notes
def print_notices(self):
'''Using the notice format, return a formatted string'''
info = ''
warnings = ''
errors = ''
hints = ''
for notice in self.notices:
if notice.level == 'info':
info = info + notice.message
if notice.level == 'warning':
warnings = warnings + notice.message
if notice.level == 'error':
errors = errors + notice.message
if notice.level == 'hint':
hints = hints + notice.message
notice_msg = formats.notice_format.format(
origin=self.origin_str,
info=info,
warnings=warnings,
errors=errors,
hints=hints)
return notice_msg
notes = notes + print_full_report(layer.import_image)
else:
for layer_origin in layer.origins.origins:
notes = notes + content.print_notices(layer_origin,
'\t', '\t\t')
layer_pkg_list = []
layer_license_list = []
for package in layer.packages:
pkg = package.name + "-" + package.version
if pkg not in layer_pkg_list and pkg:
layer_pkg_list.append(pkg)
if package.pkg_license not in layer_license_list and \
package.pkg_license:
layer_license_list.append(package.pkg_license)
# Collect packages + licenses in the layer
notes = notes + formats.layer_packages_list.format(
list=", ".join(layer_pkg_list) if layer_pkg_list else 'None')
notes = notes + formats.layer_licenses_list.format(list=", ".join(
layer_license_list) if layer_license_list else 'None')
notes = notes + formats.package_demarkation
return notes
logger.debug('Setting up...')
report.setup(dockerfile=args.dockerfile)
# attempt to build the image
logger.debug('Building Docker image...')
# placeholder to check if we can analyze the full image
completed = True
build, _ = dhelper.is_build()
if build:
# attempt to get built image metadata
image_tag_string = dhelper.get_dockerfile_image_tag()
full_image = report.load_full_image(image_tag_string)
if full_image.origins.is_empty():
# image loading was successful
# Add an image origin here
full_image.origins.add_notice_origin(
formats.dockerfile_image.format(dockerfile=args.dockerfile))
# analyze image
analyze(full_image, args, True)
else:
# we cannot load the full image
logger.warning('Cannot retrieve full image metadata')
completed = False
# clean up image
container.remove_image(full_image.repotag)
if not args.keep_wd:
report.clean_image_tars(full_image)
else:
# cannot build the image
logger.warning('Cannot build image')
completed = False
# check if we have analyzed the full image or not
if not completed:
looking up in cache and if not there then looking up in the command
library. For looking up in command library first mount the filesystem
and then look up the command library for commands to run in chroot'''
# find the layers that are imported
if dockerfile:
dhelper.set_imported_layers(image_obj)
# add notices for each layer if it is imported
image_setup(image_obj)
shell = ''
# set up empty master list of packages
master_list = []
# find the binary by mounting the base layer
target = rootfs.mount_base_layer(image_obj.layers[0].tar_file)
binary = common.get_base_bin()
# set up a notice origin referring to the base command library listing
origin_command_lib = formats.invoking_base_commands
# set up a notice origin for the first layer
origin_first_layer = 'Layer: ' + image_obj.layers[0].fs_hash[:10]
# find the shell to invoke commands in
shell, _ = command_lib.get_image_shell(
command_lib.get_base_listing(binary))
if not shell:
# add a warning notice for no shell in the command library
logger.warning('No shell listing in command library. '
'Using default shell')
no_shell_message = errors.no_shell_listing.format(
binary=binary, default_shell=constants.shell)
image_obj.layers[0].origins.add_notice_to_origins(
origin_command_lib, Notice(no_shell_message, 'warning'))
# add a hint notice to add the shell to the command library
add_shell_message = errors.no_listing_for_base_key.format(
listing_key='shell')
image_layer.origins.add_notice_to_origins(origin_layer, Notice(
errors.no_etc_release, 'warning'))
else:
# We make a guess about the OS based on pkg_format + binary
# First check that binary exists in base.yml
if not pkg_format or not os_guess:
image_layer.origins.add_notice_to_origins(
origin_command_lib, Notice(
errors.no_listing_for_base_key.format(listing_key=binary),
'warning'))
else:
# Assign image layer attributes and guess OS
image_layer.pkg_format = pkg_format
image_layer.os_guess = os_guess
image_layer.origins.add_notice_to_origins(origin_layer, Notice(
formats.os_style_guess.format(
package_manager=binary,
package_format=image_layer.pkg_format,
os_list=image_layer.os_guess), 'info'))