civics-cdf-validator 1.49.dev14__py3-none-any.whl → 1.49.dev16__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -84,7 +84,6 @@ class ElectionInfo(ElectionException):
84
84
 
85
85
  def get_parent_hierarchy_object_id_str(elt):
86
86
  """Get the elt path from the 1st parent with an objectId / ElectionReport."""
87
-
88
87
  elt_hierarchy = []
89
88
  current_elt = elt
90
89
  while current_elt is not None:
@@ -203,4 +202,3 @@ def severities_names():
203
202
  for exp in ExceptionListWrapper.SUPPORTED_SEVERITIES:
204
203
  names.append(exp.description.lower())
205
204
  return names
206
-
@@ -2365,17 +2365,24 @@ class OfficesHaveJurisdictionID(base.BaseRule):
2365
2365
  return ["Office"]
2366
2366
 
2367
2367
  def check(self, element):
2368
- jurisdiction_values = get_entity_info_for_value_type(
2369
- element, "jurisdiction-id"
2370
- )
2368
+ jurisdiction_values = []
2369
+ post_office_split_jurisdiction_element = element.find("JurisdictionId")
2370
+ if element_has_text(post_office_split_jurisdiction_element):
2371
+ jurisdiction_values.append(post_office_split_jurisdiction_element.text)
2372
+ else:
2373
+ jurisdiction_values = get_entity_info_for_value_type(
2374
+ element, "jurisdiction-id"
2375
+ )
2376
+
2371
2377
  jurisdiction_values = [j_id for j_id in jurisdiction_values if j_id.strip()]
2372
2378
  if not jurisdiction_values:
2373
2379
  raise loggers.ElectionError.from_message(
2374
- "Office is missing a jurisdiction-id.", [element]
2380
+ "Office is missing a jurisdiction ID.", [element]
2375
2381
  )
2376
2382
  if len(jurisdiction_values) > 1:
2377
2383
  raise loggers.ElectionError.from_message(
2378
- "Office has more than one jurisdiction-id.", [element]
2384
+ "Office has more than one jurisdiction ID.",
2385
+ [element],
2379
2386
  )
2380
2387
 
2381
2388
 
@@ -2431,11 +2438,17 @@ class OfficesHaveValidOfficeLevel(base.BaseRule):
2431
2438
  return ["Office"]
2432
2439
 
2433
2440
  def check(self, element):
2434
- office_levels = [
2435
- ol_id.strip()
2436
- for ol_id in get_external_id_values(element, "office-level")
2437
- if ol_id.strip()
2438
- ]
2441
+ office_levels = []
2442
+ post_office_split_office_level_element = element.find("Level")
2443
+ if element_has_text(post_office_split_office_level_element):
2444
+ office_levels.append(post_office_split_office_level_element.text)
2445
+ else:
2446
+ office_levels = [
2447
+ ol_id.strip()
2448
+ for ol_id in get_external_id_values(element, "office-level")
2449
+ if ol_id.strip()
2450
+ ]
2451
+
2439
2452
  if not office_levels:
2440
2453
  raise loggers.ElectionError.from_message(
2441
2454
  "Office is missing an office level.",
@@ -2461,10 +2474,13 @@ class OfficesHaveValidOfficeRole(base.BaseRule):
2461
2474
  return ["Office"]
2462
2475
 
2463
2476
  def check(self, element):
2464
- office_roles = [
2465
- office_role.strip()
2466
- for office_role in get_external_id_values(element, "office-role")
2467
- ]
2477
+ office_roles = [role.text for role in element.findall("Role")]
2478
+ if not office_roles:
2479
+ office_roles = [
2480
+ office_role.strip()
2481
+ for office_role in get_external_id_values(element, "office-role")
2482
+ ]
2483
+
2468
2484
  if not office_roles:
2469
2485
  raise loggers.ElectionError.from_message(
2470
2486
  "Office is missing an office role.",
@@ -3002,8 +3018,10 @@ class RemovePersonAndOfficeHolderId60DaysAfterEndDate(base.TreeRule):
3002
3018
  self.election_tree, "OfficeHolderTenure"
3003
3019
  )
3004
3020
  for officeholder_tenure in officeholder_tenures:
3005
- person_id = officeholder_tenure.find("OfficeHolderPersonId").text
3006
- object_id = officeholder_tenure.get("objectId")
3021
+ office_holder_person_elem = officeholder_tenure.find(
3022
+ "OfficeHolderPersonId"
3023
+ )
3024
+ person_id = office_holder_person_elem.text
3007
3025
  date_validator = base.DateRule(None, None)
3008
3026
  date_validator.gather_dates(officeholder_tenure)
3009
3027
  end_date = date_validator.end_date
@@ -3017,13 +3035,15 @@ class RemovePersonAndOfficeHolderId60DaysAfterEndDate(base.TreeRule):
3017
3035
  sixty_days_earlier.day,
3018
3036
  )
3019
3037
  if end_date < partial_date_sixty_days:
3020
- outdated_officeholder_tenures.append(object_id)
3038
+ outdated_officeholder_tenures.append(officeholder_tenure)
3021
3039
  if person_id in outdated_officetenure_persons.keys():
3022
3040
  outdated_officetenure_persons[person_id].append(
3023
- (object_id, end_date)
3041
+ (office_holder_person_elem, end_date)
3024
3042
  )
3025
3043
  else:
3026
- outdated_officetenure_persons[person_id] = [(object_id, end_date)]
3044
+ outdated_officetenure_persons[person_id] = [
3045
+ (office_holder_person_elem, end_date)
3046
+ ]
3027
3047
  for outdated_officeholder_tenure in outdated_officeholder_tenures:
3028
3048
  info_message = (
3029
3049
  "The officeholder tenure end date is more than 60 days"
@@ -3035,7 +3055,9 @@ class RemovePersonAndOfficeHolderId60DaysAfterEndDate(base.TreeRule):
3035
3055
  )
3036
3056
  for person_id, value_list in outdated_officetenure_persons.items():
3037
3057
  has_recent_tenure = False
3058
+ office_holder_person_elem = None
3038
3059
  for value in value_list:
3060
+ office_holder_person_elem = value[0]
3039
3061
  end_date = value[1]
3040
3062
  sixty_days_earlier = datetime.datetime.now() + datetime.timedelta(
3041
3063
  days=-60
@@ -3047,13 +3069,15 @@ class RemovePersonAndOfficeHolderId60DaysAfterEndDate(base.TreeRule):
3047
3069
  )
3048
3070
  if end_date > partial_date_sixty_days:
3049
3071
  has_recent_tenure = True
3050
- if not has_recent_tenure:
3072
+ if not has_recent_tenure and office_holder_person_elem is not None:
3051
3073
  info_message = (
3052
3074
  "All officeholder tenures ended more than 60 days ago. "
3053
- "Therefore, you can remove the person and the related "
3054
- "officeholder tenures from the feed."
3075
+ "Therefore, you can remove the person and the "
3076
+ "related officeholder tenures from the feed."
3077
+ )
3078
+ info_log.append(
3079
+ loggers.LogEntry(info_message, [office_holder_person_elem])
3055
3080
  )
3056
- info_log.append(loggers.LogEntry(info_message, [person_id]))
3057
3081
  else:
3058
3082
  for office in offices:
3059
3083
  person_id = office.find("OfficeHolderPersonIds").text
@@ -5,4 +5,4 @@ No dependencies should be added to this module.
5
5
  See https://packaging.python.org/guides/single-sourcing-package-version/
6
6
  """
7
7
 
8
- __version__ = '1.49.dev14'
8
+ __version__ = '1.49.dev16'
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: civics_cdf_validator
3
- Version: 1.49.dev14
3
+ Version: 1.49.dev16
4
4
  Summary: Checks if an election feed follows best practices
5
5
  Home-page: https://github.com/google/civics_cdf_validator
6
6
  Author: Google Civics
@@ -1,15 +1,15 @@
1
1
  civics_cdf_validator/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
2
2
  civics_cdf_validator/base.py,sha256=5zntjAdAA-bdwYOOStFgUle9LGX_ccelS--thMhUG9A,16954
3
3
  civics_cdf_validator/gpunit_rules.py,sha256=Cg-qlOeVKTCQ5qUKYSxbVrrh3tdLt1X5Eg-7uyyR_SY,9487
4
- civics_cdf_validator/loggers.py,sha256=LS6U9YWzu72V2Q0PwyE9xE03Ul392UAPRnrp2uRBMLA,6923
4
+ civics_cdf_validator/loggers.py,sha256=ZfWFd9yskcd2-qb83EPz7eqa1iGO8BRFMtDZeE1hofA,6921
5
5
  civics_cdf_validator/office_utils.py,sha256=aFxcFQZF2oBn0gPXt_kv1LxHGvwzABScT8X5yaYtVLw,2705
6
- civics_cdf_validator/rules.py,sha256=FZmaGEm52iPFbvDQqvVFc3BZT7SyNOARJ-x7_3qVKwo,162747
6
+ civics_cdf_validator/rules.py,sha256=vJ5MkZF4FcwBg4WIDV7eiJal80E4dbIIJPP4E72ZaHg,163644
7
7
  civics_cdf_validator/stats.py,sha256=YNqv3Khkt_hJxCIunFBRSl23oXqu5gNjCmWMHFbAcSU,3819
8
8
  civics_cdf_validator/validator.py,sha256=2nwlFfQ9AmpTaO5n5ekaO845Rm0JPjNF-Il6FJW_50k,12678
9
- civics_cdf_validator/version.py,sha256=3STupAz7hHTsISiw-I-GyuKq9Tt4pHJgyls1yJfSqWM,189
10
- civics_cdf_validator-1.49.dev14.dist-info/licenses/LICENSE-2.0.txt,sha256=z8d0m5b2O9McPEK1xHG_dWgUBT6EfBDz6wA0F7xSPTA,11358
11
- civics_cdf_validator-1.49.dev14.dist-info/METADATA,sha256=GsP5SO8H7qeVl2huG8vo976TUBpIWNu8Jh8JtXJioY8,1009
12
- civics_cdf_validator-1.49.dev14.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
13
- civics_cdf_validator-1.49.dev14.dist-info/entry_points.txt,sha256=QibgvtMOocwDi7fQ1emgMJ2lIlI41sW0__KIQdnVn90,77
14
- civics_cdf_validator-1.49.dev14.dist-info/top_level.txt,sha256=PYT5Eclxbop5o6DJIcgs4IeU6Ds5jqyftjoFbgkkJYo,21
15
- civics_cdf_validator-1.49.dev14.dist-info/RECORD,,
9
+ civics_cdf_validator/version.py,sha256=ZCxiUD6TuAAC6J4lrdJKqCjSsBp2DZgubMOEktKezks,189
10
+ civics_cdf_validator-1.49.dev16.dist-info/licenses/LICENSE-2.0.txt,sha256=z8d0m5b2O9McPEK1xHG_dWgUBT6EfBDz6wA0F7xSPTA,11358
11
+ civics_cdf_validator-1.49.dev16.dist-info/METADATA,sha256=GlQSyUJt23C6yB6yIS0X678MG60Zi7IRDQa1LH2vgfM,1009
12
+ civics_cdf_validator-1.49.dev16.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
13
+ civics_cdf_validator-1.49.dev16.dist-info/entry_points.txt,sha256=QibgvtMOocwDi7fQ1emgMJ2lIlI41sW0__KIQdnVn90,77
14
+ civics_cdf_validator-1.49.dev16.dist-info/top_level.txt,sha256=PYT5Eclxbop5o6DJIcgs4IeU6Ds5jqyftjoFbgkkJYo,21
15
+ civics_cdf_validator-1.49.dev16.dist-info/RECORD,,