示例#1
0
    def test_clone_repo_fail_clone(self, git_mock):
        repo_dir = '/does/not/matter'
        repo_url = '[email protected]:/foo/test.git'
        username = '******'
        password = '******'

        git_mock.clone.side_effect = create_sh_side_effect(
            exception=sh.ErrorReturnCode('git', b'mock out',
                                         b'mock git clone error'))

        with self.assertRaisesRegex(
                StepRunnerException,
                re.compile(
                    rf"Error cloning repository \({repo_url}\):"
                    r".*RAN: git"
                    r".*STDOUT:"
                    r".*mock out"
                    r".*STDERR:"
                    r".*mock git clone error", re.DOTALL)):
            clone_repo(repo_dir=repo_dir,
                       repo_url=repo_url,
                       username=username,
                       password=password)

            git_mock.clone.assert_called_once_with(repo_url,
                                                   repo_dir,
                                                   _out=ANY,
                                                   _err=ANY)
示例#2
0
    def test_git_commit_file_fail_commit(self, git_mock):
        git_mock.commit.side_effect = create_sh_side_effect(
            exception=sh.ErrorReturnCode('git', b'mock out',
                                         b'mock git commit error'))

        with self.assertRaisesRegex(
                StepRunnerException,
                re.compile(
                    r"Unexpected error commiting file \(charts/foo/values-DEV.yaml\)"
                    r" in git repository \(/does/not/matter\):"
                    r".*RAN: git"
                    r".*STDOUT:"
                    r".*mock out"
                    r".*STDERR:"
                    r".*mock git commit error", re.DOTALL)):
            git_commit_file(git_commit_message='hello world',
                            file_path='charts/foo/values-DEV.yaml',
                            repo_dir='/does/not/matter')

            git_mock.add.assert_called_once_with('charts/foo/values-DEV.yaml',
                                                 _cwd='/does/not/matter',
                                                 _out=ANY,
                                                 _err=ANY)

            git_mock.commit.assert_called_once_with('--allow-empty',
                                                    '--all',
                                                    '--message',
                                                    'hello world',
                                                    _cwd='/does/not/matter',
                                                    _out=ANY,
                                                    _err=ANY)
示例#3
0
    def test_git_tag_and_push_fail_push_tag(self, git_mock):
        repo_dir = '/does/not/matter'
        tag = 'v0.42.0'
        url = None

        git_mock.push.side_effect = [
            create_sh_side_effect(),
            sh.ErrorReturnCode('git', b'mock out', b'mock git push tag error')
        ]

        with self.assertRaisesRegex(
                StepRunnerException,
                re.compile(
                    rf"Error pushing tags from repository directory \({repo_dir}\) to"
                    rf" repository \({url}\):"
                    r".*RAN: git"
                    r".*STDOUT:"
                    r".*mock out"
                    r".*STDERR:"
                    r".*mock git push tag error", re.DOTALL)):
            git_tag_and_push(repo_dir=repo_dir, tag=tag, url=url)

            git_mock.push.bake().assert_has_calls([
                call(_cwd=repo_dir, _out=ANY),
                call('--tag', _cwd=repo_dir, _out=ANY)
            ])

            git_mock.tag.assert_called_once_with(tag,
                                                 '-f',
                                                 _cwd=repo_dir,
                                                 _out=ANY,
                                                 _err=ANY)
示例#4
0
    def test___get_oscap_document_type_xccdf(self, oscap_mock):
        oscap_input_file = '/does/not/matter.xml'

        sh.oscap.info.side_effect = create_sh_side_effect(mock_stdout="""
Document type: XCCDF Checklist
Checklist version: 1.1
Imported: 2020-02-11T13:41:07
Status: draft
Generated: 2020-02-11
Resolved: true
Profiles:
	Title: Protection Profile for General Purpose Operating Systems
		Id: ospp
	Title: PCI-DSS v3.2.1 Control Baseline for Red Hat Enterprise Linux 8
		Id: pci-dss
	Title: [DRAFT] DISA STIG for Red Hat Enterprise Linux 8
		Id: stig
	Title: Australian Cyber Security Centre (ACSC) Essential Eight
		Id: e8
Referenced check files:
	ssg-rhel8-oval.xml
		system: http://oval.mitre.org/XMLSchema/oval-definitions-5
	ssg-rhel8-ocil.xml
		system: http://scap.nist.gov/schema/ocil/2
	https://www.redhat.com/security/data/oval/com.redhat.rhsa-RHEL8.xml
		system: http://oval.mitre.org/XMLSchema/oval-definitions-5""")

        oscap_document_type = OpenSCAPGeneric._OpenSCAPGeneric__get_oscap_document_type(
            oscap_input_file=oscap_input_file)

        sh.oscap.info.assert_called_once_with(oscap_input_file,
                                              _out=Any(IOBase))

        self.assertEqual(oscap_document_type, 'XCCDF Checklist')
示例#5
0
    def test___get_oscap_document_type_sds(self, oscap_mock):
        oscap_input_file = '/does/not/matter.xml'

        sh.oscap.info.side_effect = create_sh_side_effect(mock_stdout="""
Document type: Source Data Stream
Imported: 2020-10-07T05:34:29

Stream: scap_org.open-scap_datastream_from_xccdf_com.redhat.rhsa-all.xml-xccdf12
Generated: (null)
Version: 1.2
Checklists:
	Ref-Id: scap_org.open-scap_cref_com.redhat.rhsa-all.xml-xccdf12
		Status: incomplete
		Resolved: true
		Profiles:
		Referenced check files:
			com.redhat.rhsa-all.xml
				system: http://oval.mitre.org/XMLSchema/oval-definitions-5
Checks:
	Ref-Id: scap_org.open-scap_cref_com.redhat.rhsa-all.xml
No dictionaries.""")

        oscap_document_type = OpenSCAPGeneric._OpenSCAPGeneric__get_oscap_document_type(
            oscap_input_file=oscap_input_file)

        sh.oscap.info.assert_called_once_with(oscap_input_file,
                                              _out=Any(IOBase))

        self.assertEqual(oscap_document_type, 'Source Data Stream')
示例#6
0
    def test___get_oscap_document_type_oval(self, oscap_mock):
        oscap_input_file = '/does/not/matter.xml'

        sh.oscap.info.side_effect = create_sh_side_effect(mock_stdout="""
Document type: OVAL Definitions
OVAL version: 5.10
Generated: 2020-10-06T23:36:01
Imported: 2020-10-06T23:36:04""")

        oscap_document_type = OpenSCAPGeneric._OpenSCAPGeneric__get_oscap_document_type(
            oscap_input_file=oscap_input_file)

        oscap_document_type = OpenSCAPGeneric._OpenSCAPGeneric__get_oscap_document_type(
            oscap_input_file=oscap_input_file)

        self.assertEqual(oscap_document_type, 'OVAL Definitions')
示例#7
0
    def test___buildah_mount_container_success(self, buildah_mock):
        buildah_unshare_comand = sh.buildah.bake('unshare')
        container_name = "test"

        expected_mount_path = '/this/is/a/path'
        buildah_mock.bake('unshare').bake(
            'buildah', 'mount').side_effect = create_sh_side_effect(
                mock_stdout=f"{expected_mount_path}", )

        container_mount_path = OpenSCAPGeneric._OpenSCAPGeneric__buildah_mount_container(
            buildah_unshare_comand=buildah_unshare_comand,
            container_id=container_name)

        self.assertEqual(container_mount_path, expected_mount_path)

        buildah_mock.bake('unshare').bake(
            'buildah', 'mount').assert_called_once_with('--storage-driver',
                                                        'vfs',
                                                        container_name,
                                                        _out=Any(IOBase),
                                                        _err=Any(IOBase),
                                                        _tee='err')
    def test_run_step_failure(
            self,
            mock_argocd,
            argocd_sign_in_mock,
            get_app_name_mock
    ):
        with TempDirectory() as temp_dir:
            # Test setup: Test inputs / mocks
            parent_work_dir_path = os.path.join(temp_dir.path, 'working')

            argocd_cascade = True
            argocd_propagation_policy = 'background'
            environment = 'PROD'

            step_config = {
                'argocd-username': '******',
                'argocd-password': '******',
                'argocd-api': 'https://argo.ploigos.xyz',
                'argocd-skip-tls': False,
                'argocd-cascade': argocd_cascade,
                'argocd-propagation-policy': argocd_propagation_policy
            }

            # Test setup: Expected outputs
            delete_error_return = sh.ErrorReturnCode('argocd', b'mock out', b'mock argocd sign-in failure')
            delete_failure_error_msg = f"Error deleting ArgoCD app (test-app-name): {delete_error_return}"
            delete_exception = StepRunnerException(delete_failure_error_msg)

            expected_step_result = StepResult(
                step_name='delete',
                sub_step_name='ArgoCDDelete',
                sub_step_implementer_name='ArgoCDDelete',
                environment=environment
            )
            expected_step_result.success = False
            expected_step_result.message = f"Error deleting environment ({environment}):" \
                                           f" {str(delete_exception)}"
            expected_step_result.add_artifact(
                name='argocd-app-name',
                value='test-app-name'
            )

            # Test setup: Mock behaviors
            mock_argocd.app.delete.side_effect = create_sh_side_effect(
                exception=delete_error_return
            )

            # Test execution
            step_implementer = self.create_step_implementer(
                step_config=step_config,
                parent_work_dir_path=parent_work_dir_path,
                environment='PROD'
            )
            actual_step_results = step_implementer._run_step()

            # Test verification: Step results
            self.assertEqual(actual_step_results, expected_step_result)

            # Test verification: Mock method calls
            get_app_name_mock.assert_called_once_with()
            argocd_sign_in_mock.assert_called_once_with(
                argocd_api=step_config['argocd-api'],
                username=step_config['argocd-username'],
                password=step_config['argocd-password'],
                insecure=step_config['argocd-skip-tls']
            )
示例#9
0
    def __run_test___run_oscap_scan_xccdf_do_not_fetch_remote_with_profile_all_pass(
            self,
            buildah_mock,
            oscap_eval_type,
            oscap_fetch_remote_resources,
            oscap_stdout,
            oscap_stdout_expected,
            oscap_profile=None,
            oscap_tailoring_file=None,
            oscap_eval_success_expected=True,
            exit_code=0,
            oscap_eval_fails_expected=None):
        with TempDirectory() as temp_dir:
            buildah_unshare_comand = sh.buildah.bake('unshare')
            oscap_input_file = '/does/not/matter/input.xml'
            oscap_out_file_path = os.path.join(temp_dir.path, 'out')
            oscap_xml_results_file_path = '/does/not/matter/results.xml'
            oscap_html_report_path = '/does/not/matter/results.html'
            container_mount_path = '/does/not/matter/coutainer_mount'

            exception = None
            if exit_code == 2:
                exception = sh.ErrorReturnCode_2(
                    'oscap-chroot eval', bytes(oscap_stdout, 'utf-8'),
                    bytes(f'mock error - exit code {exit_code}', 'utf-8'))
            elif exit_code == 1:
                exception = sh.ErrorReturnCode_1(
                    'oscap-chroot eval', bytes(oscap_stdout, 'utf-8'),
                    bytes(f'mock error - exit code {exit_code}', 'utf-8'))
            elif exit_code:
                exception = sh.ErrorReturnCode(
                    'oscap-chroot eval', bytes(oscap_stdout, 'utf-8'),
                    bytes(f'mock error - exit code {exit_code}', 'utf-8'))

            buildah_mock.bake('unshare').bake(
                'oscap-chroot').side_effect = create_sh_side_effect(
                    mock_stdout=oscap_stdout, exception=exception)

            stdout_buff = StringIO()
            with redirect_stdout(stdout_buff):
                oscap_eval_success, oscap_eval_fails = OpenSCAPGeneric._OpenSCAPGeneric__run_oscap_scan(
                    buildah_unshare_comand=buildah_unshare_comand,
                    oscap_eval_type=oscap_eval_type,
                    oscap_input_file=oscap_input_file,
                    oscap_out_file_path=oscap_out_file_path,
                    oscap_xml_results_file_path=oscap_xml_results_file_path,
                    oscap_html_report_path=oscap_html_report_path,
                    container_mount_path=container_mount_path,
                    oscap_profile=oscap_profile,
                    oscap_tailoring_file=oscap_tailoring_file,
                    oscap_fetch_remote_resources=oscap_fetch_remote_resources)

            if oscap_profile:
                oscap_profile_flag = f"--profile={oscap_profile}"
            else:
                oscap_profile_flag = None

            if oscap_fetch_remote_resources:
                oscap_fetch_remote_resources_flag = "--fetch-remote-resources"
            else:
                oscap_fetch_remote_resources_flag = None

            if oscap_tailoring_file:
                oscap_tailoring_file_flag = f"--tailoring-file={oscap_tailoring_file}"
            else:
                oscap_tailoring_file_flag = None

            buildah_mock.bake('unshare').bake.assert_called_with(
                'oscap-chroot')
            buildah_mock.bake('unshare').bake(
                'oscap-chroot').assert_called_once_with(
                    container_mount_path,
                    oscap_eval_type,
                    'eval',
                    oscap_profile_flag,
                    oscap_fetch_remote_resources_flag,
                    oscap_tailoring_file_flag,
                    f'--results={oscap_xml_results_file_path}',
                    f'--report={oscap_html_report_path}',
                    oscap_input_file,
                    _out=Any(IOBase),
                    _err=Any(IOBase),
                    _tee='err')

            self.assertEqual(oscap_eval_success, oscap_eval_success_expected)

            if oscap_eval_fails_expected:
                self.assertEqual(oscap_eval_fails, oscap_eval_fails_expected)

            stdout = stdout_buff.getvalue()
            self.assertEqual(stdout, oscap_stdout_expected)