Conditions | 15 |
Total Lines | 91 |
Code Lines | 63 |
Lines | 0 |
Ratio | 0 % |
Tests | 0 |
CRAP Score | 240 |
Changes | 0 |
Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.
For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.
Commonly applied refactorings include:
If many parameters/temporary variables are present:
Complex classes like compose_ds.move_patches_up_to_date_to_source_data_stream_component() often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes.
Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.
1 | #!/usr/bin/python3 |
||
75 | def move_patches_up_to_date_to_source_data_stream_component(datastreamtree): |
||
76 | ds_checklists = datastreamtree.find( |
||
77 | ".//{%s}checklists" % datastream_namespace) |
||
78 | checklists_component_ref = ds_checklists.find( |
||
79 | "{%s}component-ref" % datastream_namespace) |
||
80 | checklists_component_ref_id = checklists_component_ref.get('id') |
||
81 | # The component ID is the component-ref href without leading '#' |
||
82 | checklists_component_id = checklists_component_ref.get( |
||
83 | '{%s}href' % xlink_namespace)[1:] |
||
84 | |||
85 | # Locate the <xccdf:check> element of an <xccdf:Rule> with id |
||
86 | # security_patches_up_to_date |
||
87 | checklist_component = None |
||
88 | oval_check = None |
||
89 | ds_components = datastreamtree.findall( |
||
90 | ".//{%s}component" % datastream_namespace) |
||
91 | for ds_component in ds_components: |
||
92 | if ds_component.get('id') == checklists_component_id: |
||
93 | checklist_component = ds_component |
||
94 | if checklist_component is None: |
||
95 | # Something strange happened |
||
96 | sys.stderr.write( |
||
97 | "Couldn't find <component> %s referenced by <component-ref> %s" % ( |
||
98 | checklists_component_id, checklists_component_ref_id)) |
||
99 | sys.exit(1) |
||
100 | |||
101 | rules = checklist_component.findall(".//{%s}Rule" % XCCDF12_NS) |
||
102 | for rule in rules: |
||
103 | if rule.get('id').endswith('rule_security_patches_up_to_date'): |
||
104 | rule_checks = rule.findall("{%s}check" % XCCDF12_NS) |
||
105 | for check in rule_checks: |
||
106 | if check.get('system') == oval_namespace: |
||
107 | oval_check = check |
||
108 | break |
||
109 | |||
110 | if oval_check is None: |
||
111 | # The component doesn't have a security patches up to date rule |
||
112 | # with an OVAL check |
||
113 | return |
||
114 | |||
115 | # SCAP 1.3 demands multi-check true if the Rules |
||
116 | # security_patches_up_to_date is evaluated by multiple OVAL patch class |
||
117 | # definitinos. See 3.2.4.3, SCAP 1.3 standard (NIST.SP.800-126r3) |
||
118 | oval_check.set('multi-check', 'true') |
||
119 | |||
120 | check_content_ref = oval_check.find('{%s}check-content-ref' % XCCDF12_NS) |
||
121 | href_url = check_content_ref.get('href') |
||
122 | |||
123 | # Use URL's path to define the component name and URI |
||
124 | # Path attribute returned from urlparse contains a leading '/', when |
||
125 | # mangling it it will get replaced by '-'. Let's strip the '/' to avoid |
||
126 | # a sequence of "_-" in the component-ref ID. |
||
127 | component_ref_name = mangle_path(urlparse(href_url).path[1:]) |
||
128 | component_ref_uri = component_ref_prefix + component_ref_name |
||
129 | |||
130 | # update @href to refer the datastream component name |
||
131 | check_content_ref.set('href', component_ref_name) |
||
132 | |||
133 | # Add a uri refering the component in Rule's Benchmark component-ref |
||
134 | # catalog |
||
135 | uri_exists = False |
||
136 | catalog = checklists_component_ref.find('{%s}catalog' % cat_namespace) |
||
137 | uris = catalog.findall("{%s}uri" % cat_namespace) |
||
138 | for uri in uris: |
||
139 | if uri.get('name') == component_ref_name: |
||
140 | uri_exists = True |
||
141 | return |
||
142 | if not uri_exists: |
||
143 | uri = ET.Element('{%s}uri' % cat_namespace) |
||
144 | uri.set('name', component_ref_name) |
||
145 | uri.set('uri', component_ref_uri) |
||
146 | catalog.append(uri) |
||
147 | |||
148 | # The component-ref ID is the catalog uri without leading '#' |
||
149 | component_ref_feed_id = component_ref_uri[1:] |
||
150 | |||
151 | # Add the component-ref to list of datastreams' checks |
||
152 | check_component_ref_exists = False |
||
153 | ds_checks = datastreamtree.find(".//{%s}checks" % datastream_namespace) |
||
154 | check_component_refs = ds_checks.findall( |
||
155 | "{%s}component-ref" % datastream_namespace) |
||
156 | for check_component_ref in check_component_refs: |
||
157 | if check_component_ref.get('id') == component_ref_feed_id: |
||
158 | check_component_ref_exists = True |
||
159 | return |
||
160 | if not check_component_ref_exists: |
||
161 | component_ref_feed = ET.Element( |
||
162 | '{%s}component-ref' % datastream_namespace) |
||
163 | component_ref_feed.set('id', component_ref_feed_id) |
||
164 | component_ref_feed.set('{%s}href' % xlink_namespace, href_url) |
||
165 | ds_checks.append(component_ref_feed) |
||
166 | |||
276 |