ComplianceAsCode / ComplianceAsCode/content

Cannot use firefox rules in a fedora profile with additional_content_directories

Open
#10,462 0 comments 1 reaction 0 assignees View on GitHub
triaged
Dominant language
Shell
Stars
2.8k
Forks
828
Avg merge
3d 8m
Merged PRs (30d)
80

Description

#### Description of problem:
When developing a new profile for common fedora users, I wanted to put a few firefox rules into a fedora profile using the additional_content_directories key (see https://complianceascode.readthedocs.io/en/latest/manual/developer/03_creating_content.html#benchmark-structure-layout). I added the prodtype 'fedora' to the selected firefox rules and added the firefox additional directory to the fedora product.yml, but after building the fedora product, the firefox rules were selected in the final datastream, but not showing up in the HTML guide. Also, the firefox rule OVAL checks were not present in either.

#### SCAP Security Guide Version:
Latest master , commit e4632431ad7b3e2b57c1d271c70e3d5c38825508
OpenSCAP 1.3.7

#### Operating System Version:
Fedora 37

#### Steps to Reproduce:

1. add "products/firefox/guide" additional content directory to product.yml
2. add fedora prodtype to rule firefox_policy-autoplay_video
3. add this rule to fedora standard.profile
4. build fedora product

#### Actual Results:

The resulting datastream has the firefox rule selected, but there is no check; the HTML guide does not contain the firefox rule or the firefox group

#### Expected Results:

The resulting HTML guide contains the rule firefox_policy-autoplay_video, the datastream contains both the rule as well as the OVAL check

#### Additional Information/Debugging Steps:

I used "products/firefox/guide" as the additional content directory, even though it contains a benchmark.yml file, which is prohibited according to documentation, because the path which I expected to be correct according to documentation "../products/firefox/guide/firefox", as well as other combinations did not work and gave me a FileNotFoundError.

When I only included the firefox rule in the fedora profile, without any fedora-only rules, I got "ValueError: Profile standard unselects all groups.", which led me to believe there is something broken in the buildsystem, and the groups from additional content directories are not correctly loading in. I tried to fix this myself but hit a dead end, here is my progress so far:

First, I modified the main function of build_xccdf.py, before loader.load_benchmark is called:

```
diff --git a/build-scripts/build_xccdf.py b/build-scripts/build_xccdf.py
index d272311fc5..7d23143114 100644
--- a/build-scripts/build_xccdf.py
+++ b/build-scripts/build_xccdf.py
@@ -55,16 +55,27 @@ def main():
args.build_config_yaml, args.product_yaml)
base_dir = os.path.dirname(args.product_yaml)
benchmark_root = ssg.utils.required_key(env_yaml, "benchmark_root")
+ try:
+ additional_content_directories = ssg.utils.required_key(env_yaml, "additional_content_directories")
+ except:
+ additional_content_directories = []
+ # better to add optional_key() to ssg.utils

# we have to "absolutize" the paths the right way, relative to the
# product_yaml path
if not os.path.isabs(benchmark_root):
benchmark_root = os.path.join(base_dir, benchmark_root)

+ for i in range(len(additional_content_directories)):
+ if not os.path.isabs(additional_content_directories[i]):
+ additional_content_directories[i] = os.path.join(base_dir, "../../" + additional_content_directories[i])
+ # the ../../ is needed because for some reason, benchmark_root and additional_content_directories
+ # in product.yml are evaluated from different base dir = adding the ../../ in product.yml breaks build
+
loader = ssg.build_yaml.LinearLoader(
env_yaml, args.resolved_base)
loader.load_compiled_content()
- loader.load_benchmark(benchmark_root)
+ loader.load_benchmark(benchmark_root, additional_content_directories)

loader.add_fixes_to_rules()
xccdftree = loader.export_benchmark_to_xml()
```

I loaded the additional_content_directories list from the product.yaml, normalized the paths, and sent them to the loader.load_benchmark method.

Then I modified load_benchmark in build_yaml.py accordingly, so that the extra groups would also be loaded:

```
diff --git a/ssg/build_yaml.py b/ssg/build_yaml.py
index 375ba02ebe..7721b161ff 100644
--- a/ssg/build_yaml.py
+++ b/ssg/build_yaml.py
@@ -1411,7 +1411,7 @@ class LinearLoader(object):
for rule_id, rule_fixes in self.fixes.items():
self.rules[rule_id].add_fixes(rule_fixes)

- def load_benchmark(self, directory):
+ def load_benchmark(self, directory, additional_content_directories):
self.benchmark = Benchmark.from_yaml(
os.path.join(directory, "benchmark.yml"), self.env_yaml, self.product_cpes)

@@ -1419,6 +1419,10 @@ class LinearLoader(object):
self.resolved_profiles_dir, self.env_yaml, self.product_cpes)

benchmark_first_groups = self.find_first_groups_ids(directory)
+
+ for additional_dir in additional_content_directories:
+ benchmark_first_groups += self.find_first_groups_ids(additional_dir)
+
for gid in benchmark_first_groups:
try:
self.benchmark.add_group(self.groups[gid], self.env_yaml, self.product_cpes)
```

After this, the firefox group and rules were showing up in the HTML guide, but the OVAL checks were not present.

I saw that the checks from additional content directories were supposed to load in build_ovals.py function _get_checks_from_benchmark, however the firefox group path getting loaded was not correct, so I tried to fix it:

```
diff --git a/ssg/build_ovals.py b/ssg/build_ovals.py
index 5e6099c546..2648d00112 100644
--- a/ssg/build_ovals.py
+++ b/ssg/build_ovals.py
@@ -330,7 +330,7 @@ class OVALBuilder:
"additional_content_directories", [])
dirs_to_scan = [guide_dir]
for rd in additional_content_directories:
- abspath = os.path.abspath(os.path.join(product_dir, rd))
+ abspath = os.path.abspath(os.path.join(product_dir, "../../" + rd))
dirs_to_scan.append(abspath)
rule_dirs = list(find_rule_dirs_in_paths(dirs_to_scan))
oval_checks = self._process_directories(rule_dirs, True)
```

However after attempting bunch of other stuff, I got nowhere. Maybe I am misunderstanding how the additional_content_directories key is supposed to work? Thanks for any help :-)

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.