コード例 #1
0
ファイル: Family.py プロジェクト: 39xdgy/Final_Project_SW555
    def birth_before_death_of_parents(self):
        if not self._husband or not self._wife:
            raise AttributeError("Missing husband/wife")
        if not self._husband.get_deathDate() and not self._wife.get_deathDate(
        ):
            return True
        if len(self._children) == 0: return True
        death = self._wife.get_deathDate()
        hDeath = self._husband.get_deathDate()
        if not hDeath:
            for c in self._children:
                if c.get_birthDate() > death:
                    #return False
                    raise Error(
                        'ERROR', 'FAMILY', 'US09',
                        c.get_lineNum()["BIRT"],
                        f"Child birthday {c.get_birthDate()} is after death date of mother {death}"
                    )
            return True
        # hDeath = hDeath + (0, 9, 0)
        # if hDeath[1] > 12:
        #     hDeath[1] = hDeath[1] % 12
        #     hDeath[0] = hDeath[0] + 1
        # if not death:
        #     for c in self._children:
        #         if c.get_birthDate() > hDeath:
        #             # return False
        #             raise Error('ERROR', 'FAMILY', 'US09', c.get_lineNum()['BIRT'],
        #                         f"Child birthday {c.get_birthDate()} is after 9 month of death date of father {hDeath}")
        #     return True
        # if hDeath < death:
        #     if not death and not hDeath:
        #         return True
        if hDeath:
            hDeath = list(map(sum, zip(hDeath, (0, 9, 0))))
            if hDeath[1] > 12:
                hDeath[1] = hDeath[1] % 12
                hDeath[0] = hDeath[0] + 1

        hDeath = tuple(hDeath)
        if death is None or hDeath < death:
            death = hDeath
        death = tuple(death)
        for c in self._children:
            if c.get_birthDate() > death:
                # return False
                raise Error(
                    'ERROR', 'FAMILY', 'US09',
                    c.get_lineNum()['BIRT'],
                    f"Child birthday {c.get_birthDate()} is after 9 month of death date of father {hDeath}"
                )
        return True
コード例 #2
0
 def update_name(self, name):
     if len(name) < 3:
         return Error("Name must be at least 3 characters long.",
                      "Name parameter must be at least 3 characters long.",
                      400, "https://en.wikipedia.org/wiki/HTTP_400")
     elif len(name) > 255:
         return Error(
             "Name cannot be longer than 255 characters.",
             "Name parameter cannot be longer than 255 characters.", 400,
             "https://en.wikipedia.org/wiki/HTTP_400")
     self.name = name
     db.session.commit()
     return self
コード例 #3
0
    def unique_families_by_spouses(self):
        check_list = []
        for _, family in self._families:
            if not family.get_husband() or not family.get_wife():
                raise AttributeError("no husband or wife")
            if not family.get_husband().get_name() or not family.get_wife(
            ).get_name():
                raise AttributeError("no husband or wife name")
            if not family.get_marriedDate():
                raise AttributeError("no marriage date")
            this_fam_info = [
                family.get_husband().get_name(),
                family.get_wife.get_name(),
                family.get_marriedDate()
            ]
            if this_fam_info in check_list:
                # return False
                raise Error(
                    'ANOMALY', 'GEDCOM', 'US024',
                    family.get_lineNum()['FAM ID'],
                    f"Family{family.get_id()} has repeated marriage date{family.get_marriedDate()} or spouse name{family._wife.get_name()}"
                )
            check_list.append(this_fam_info)

        return True
コード例 #4
0
 def patch(self, usage_id, new_value):
     usage = UsageModel.find_by_id(usage_id)
     new_value = float(new_value)
     if usage.min_value > new_value or usage.max_value < new_value:
         return {
             "errors":
             Error(
                 "New value does not fall within the expected range. ({} - {})"
                 .format(usage.min_value, usage.max_value),
                 "{} is outside of ({} - {})".format(
                     new_value, usage.min_value,
                     usage.max_value), 422, "").to_json()
         }, 422
     print("url is: " + "{}/{}/{}".format(
         app.config['HOMELYNK_URI'], usage.external_item_id, new_value))
     response = requests.get(
         url="{}/{}/{}".format(app.config['HOMELYNK_URI'],
                               usage.external_item_id, int(new_value)))
     home_response = response.json()
     item = ItemModel.find_by_id(usage.item_id)
     item_in_json = item.to_json()
     fake_event = {
         'last_use_timestamp': datetime.now().timestamp(),
         'data_type': usage.unit.value,
         'data': float(home_response["current_value"]),
         'usage_id': usage.id
     }
     item_in_json['last_use'] = fake_event
     return item_in_json, 200
コード例 #5
0
 def less_then_150_years_old(self):
     if self.get_age() < 150: return True
     else:
         raise Error(
             'ANOMALY', 'INDIVIDUAL', 'US07',
             self.get_lineNum()['BIRT'],
             f" Individual's Age {self.get_age()} is greater than 150")
コード例 #6
0
ファイル: Family.py プロジェクト: 39xdgy/Final_Project_SW555
    def multiple_births_lessOrEqual_than_5(
            self):  # cannot catch multi multiples; not sure if need to
        from datetime import date
        today = date.today()
        try:
            births = sorted(
                list(
                    map(lambda i: abs((date(*i) - today).days),
                        [x.get_birthDate() for x in self.get_children()])))
        except AttributeError:
            raise AttributeError("Missing birthdate for children")

        if len(births) <= 5:
            return True
        multi, sameDay, pre = 0, 0, births[0]
        for i in range(len(births)):
            if pre == births[i]:
                multi += 1
                sameDay += 1
            elif births[i] - pre == 1:
                multi, sameDay = sameDay + 1, 1
            else:
                multi, sameDay = 1, 1
            pre = births[i]
            if multi >= 5:
                raise Error(
                    'ANOMALY', 'FAMILY', 'US14',
                    self.get_lineNum()["CHIL"],
                    f'Family has more than five children with the same birthday'
                )
                #return False
        return True
コード例 #7
0
ファイル: Family.py プロジェクト: 39xdgy/Final_Project_SW555
    def marriage_before_death(self):
        from datetime import date

        if not self._husband or not self._wife or not self.get_marriedDate():
            raise AttributeError("Missing husband/wife/marriedDate")
        if not self._husband.get_deathDate() and not self._wife.get_deathDate(
        ):
            return True

        death = None
        if not self._husband.get_deathDate():
            death = self._wife.get_deathDate()
        elif not self._wife.get_deathDate():
            death = self._husband.get_deathDate()

        else:
            if self._husband.get_deathDate() > self._wife.get_deathDate():
                death = self._wife.get_deathDate()
            else:
                death = self._husband.get_deathDate()
        marriage = self._marriedDate
        timedelta = date(*marriage) - date(*death)
        if timedelta.days <= 0:
            return True
        else:
            raise Error(
                'ERROR', 'FAMILY', 'US05',
                self.get_lineNum()["MARR"],
                f"Family marriage date {marriage} is after death date of husband{self._husband.get_deathDate()} or wife{self._wife.get_deathDate()}"
            )
コード例 #8
0
ファイル: Family.py プロジェクト: 39xdgy/Final_Project_SW555
    def marriage_after_14(self) -> bool:
        from datetime import date

        if not self._husband or not self._wife or not self._marriedDate:
            raise AttributeError("Missing husband/wife/marriedDate")
        if not self._husband.get_birthDate() or not self._wife.get_birthDate():
            raise AttributeError("Missing birthdate for husband/wife")

        if not self._husband or not self._wife or not self._marriedDate:
            raise AttributeError("Missing husband/wife/marriedDate")
        if not self._husband.get_birthDate() or not self._wife.get_birthDate():
            raise AttributeError("Missing birthdate for husband/wife")
        husbandMarryAge = (date(*self._marriedDate) -
                           date(*self._husband.get_birthDate())).days // 365
        wifeMarryAge = (date(*self._marriedDate) -
                        date(*self._wife.get_birthDate())).days // 365
        if (husbandMarryAge > 14 and wifeMarryAge > 14):
            return True
        else:
            raise Error(
                'ERROR', 'FAMILY', 'US10',
                self.get_lineNum()["MARR"],
                f"Family marriage date {self.get_marriedDate()} is not 14 years after"
                f"Husband birthday {self._husband.get_birthDate()} or Wife birthday {self._wife.get_birthDate()}"
            )
コード例 #9
0
 def siblings_should_not_marry(self):
     if not self._husband or not self._wife: raise AttributeError("Missing husband or wife")
     if not self._husband.get_parent_family() and not self._wife.get_parent_family(): raise AttributeError(
         "Missing husband and wife parent")
     if not self._husband.get_parent_family().get_id() == self._wife.get_parent_family().get_id():
         return True
     else:raise Error('ERROR', 'FAMILY', 'US18', self.get_lineNum()['FAM ID'], f"Siblings in family {self.get_id()} are married.")
コード例 #10
0
ファイル: Family.py プロジェクト: 39xdgy/Final_Project_SW555
    def divorce_before_death(self) -> bool:
        from datetime import date
        if not self._husband or not self._wife:
            raise AttributeError("Missing husband/wife")
        if not self._husband.get_deathDate() and not self._wife.get_deathDate(
        ):
            return True
        if not self._divorced: return True

        deathdays = None
        if self._husband.get_deathDate() and self._wife.get_deathDate():
            deathdays = (date(*self._divorced) -
                         date(*self._husband.get_deathDate())).days
            if deathdays > (date(*self._divorced) -
                            date(*self._wife.get_deathDate())).days:
                deathdays = (date(*self._divorced) -
                             date(*self._wife.get_deathDate())).days

        elif not self._husband.get_deathDate():
            deathdays = (date(*self._divorced) -
                         date(*self._wife.get_deathDate())).days
        elif not self._wife.get_deathDate():
            deathdays = (date(*self._divorced) -
                         date(*self._husband.get_deathDate())).days

        if deathdays < 0:
            return True
        else:
            raise Error(
                'ERROR', 'FAMILY', 'US05',
                self.get_lineNum()["DIV"],
                f"Family divorce date {self.get_divorcedDate()} is after death date of husband{self._husband.get_deathDate()} or wife{self._wife.get_deathDate()}"
            )
コード例 #11
0
 def order_siblings_by_age(self):
     """
     Need one extra step which filters out the Nones. Not sure if necessary.
     :return: list of references in the order of descending age
     """
     res = sorted(self.get_children(), key=lambda x: x.get_age(days=True), reverse=True)
     if list(filter(lambda x: x.get_birthDate() != None, res)):
         return True
     else: raise Error('ERROR', 'FAMILY', 'US28', self.get_lineNum()['FAM ID'], f"Family {self.get_id()} Siblings not ordered by age")
コード例 #12
0
 def fewer_than_15_siblings(self):
     """
     if self._children is empty, it is a empty list which the length is 0
     :return: boolean if the length of self._children is less then 15
     """
     if len(self._children) < 15:
         return True
     else: raise Error('ERROR', 'FAMILY', 'US15', self.get_lineNum()["FAM ID"],
                   f"The siblings of the family is more than 15.")
コード例 #13
0
    def first_cousins_should_not_marry(self):
        if not self.get_parent_family():
            raise AttributeError("missing parent family")
        if not self.get_parent_family().get_husband(
        ) or not self.get_parent_family().get_wife():
            raise AttributeError("missing husband or wife")
        if not self.get_parent_family().get_husband().get_parent_family(
        ) or not self.get_parent_family().get_wife().get_parent_family():
            raise AttributeError("missing husband/wife's parent family")

        daddy = self.get_parent_family().get_husband()
        daddy_siblings = self.get_parent_family().get_husband(
        ).get_parent_family().get_children()[:]
        daddy_siblings.remove(daddy)  # if singleton, this loop does nothing
        for daddy_sibling in daddy_siblings:
            daddy_sibling_families = daddy_sibling.get_family(
            )  # consider past families
            for child_fam in daddy_sibling_families:
                for first_cousin in child_fam.get_children():
                    if first_cousin == self:
                        #return False
                        raise Error(
                            'ANOMALY', 'INDIVIDUAL', 'US19',
                            first_cousin.get_lineNum()['INDI ID'],
                            f"first_cousin {first_cousin.get_id()} is married to each other"
                        )

        mummy = self.get_parent_family().get_wife()
        mummy_siblings = self.get_parent_family().get_wife().get_parent_family(
        ).get_children()[:]
        mummy_siblings.remove(mummy)  # if singleton, this loop does nothing
        for mummy_sibling in mummy_siblings:
            mummy_sibling_families = mummy_sibling.get_family(
            )  # consider past families
            for mummy_sibling_fam in mummy_sibling_families:
                for first_cousin in mummy_sibling_fam.get_children():
                    if first_cousin == self:
                        #return False
                        raise Error(
                            'ANOMALY', 'INDIVIDUAL', 'US19',
                            first_cousin.get_lineNum()['INDI ID'],
                            f"first_cousin {first_cousin.get_id()} is married to each other"
                        )
        return True
コード例 #14
0
    def post(self):
        errors = []
        if 'usage_id' in request.form.keys():
            usage_id = request.form['usage_id']
            data_type = request.form['data_type']
            data = request.form['data']
        else:
            request_data = json.loads(request.data)
            usage_id = request_data['usage_id']
            data_type = request_data['data_type']
            data = request_data['data']

        usage = UsageModel.find_by_id(usage_id)
        if usage is None:
            errors.append(
                Error(
                    "Cannot find usage with id: {}".format(usage_id),
                    "UsageModel.find_by_id({}) returns None".format(usage_id),
                    404, "https://en.wikipedia.org/wiki/HTTP_404"))
        if UnitEnum.has_value(data_type):
            data_type = UnitEnum(data_type)
        else:
            errors.append(
                Error(
                    '"{}" is not a valid unit type.'.format(data_type),
                    "UnitEnum.has_value({}) returned False".format(data_type),
                    400, "https://en.wikipedia.org/wiki/HTTP_400"))

        if len(errors) > 0:
            all_errors_in_json = [error.to_json() for error in errors]
            return {"errors": all_errors_in_json}, 422

        if usage.unit != data_type:
            error = Error(
                'The unit type of the usage with id "{}" does not match the given "{}".'
                .format(usage_id,
                        data_type), "usage.unit does not equal data_type.",
                422, "https://en.wikipedia.org/wiki/HTTP_422")
            return {"errors": error.to_json()}, 422

        event = EventModel(usage_id, data, round(datetime.now().timestamp()))
        event.save_to_db()
        return event.to_json(), 201
コード例 #15
0
    def dates_before_current_date(self):
        from datetime import date
        today = date.today()
        for _, indi in self._individuals:
            if not indi.get_birthDate():
                raise AttributeError("missing birthdate for individual")
            if not (today - date(indi.get_birthDate())).days < 0:
                #return False
                raise Error(
                    'ERROR', 'GEDCOM', 'US01',
                    indi.get_lineNum()['INDI ID'],
                    f"Individual{indi.get_id()}'s birthday {indi.get_birthDate()} is after today's date {today}"
                )
            if not indi.get_deathDate() == None:
                if not (today - date(indi.get_deathDate())).days < 0:
                    # return False
                    raise Error(
                        'ERROR', 'GEDCOM', 'US01',
                        indi.get_lineNum()['INDI ID'],
                        f"Individual{indi.get_id()}'s death date {indi.get_deathDate()} is after today's date {today}"
                    )

        for _, fam in self._families:
            if not fam.get_marriedDate():
                raise AttributeError("missing marriedDate for family")
            if not (today - date(fam.get_marriedDate())).days < 0:
                #return False
                raise Error(
                    'ERROR', 'GEDCOM', 'US01',
                    fam.get_lineNum()['FAM ID'],
                    f"Family{fam.get_id()}'s marriage date {fam.get_marriedDate()} is after today's date {today}"
                )
            if not fam.get_divorcedDate() == None:
                if not (today - date(fam.get_divorcedDate())).days < 0:
                    #return False
                    raise Error(
                        'ERROR', 'GEDCOM', 'US01',
                        fam.get_lineNum()['INDI ID'],
                        f"Individual{fam.get_id()}'s divorce date {fam.get_divorcedDate()} is after today's date {today}"
                    )

        return True
コード例 #16
0
    def birth_before_marriage_of_parents(self):
        if not self._husband or not self._wife: raise AttributeError("Missing husband/wife")
        if not self.get_marriedDate(): raise AttributeError("Missing marrageDate")

        for c in self._children:
            if not c.get_birthDate(): raise AttributeError("Missing child birthDate")
            if c.get_birthDate() <= self.get_marriedDate():
                # return False
                raise Error('ANOMALY', 'FAMILY', 'US08', c.get_lineNum()["BIRT"],
                            f"Child birthday {c.get_birthDate()} is after marriage date of Family {self.get_marriedDate()}")
        return True
コード例 #17
0
 def marriage_before_divorce(self):
     from datetime import date
     marriage = self.get_marriedDate()
     divorce = self.get_divorcedDate()
     if not marriage: raise AttributeError("Missing marriage date")
     if not divorce: return True
     timedelta = date(*marriage) - date(*divorce)
     if timedelta.days < 0:
         return True
     else:
         raise Error('ERROR', 'FAMILY', 'US04', self.get_lineNum()["MARR"],
                     f"Family marriage date {marriage} is after divorce date {divorce}")
コード例 #18
0
    def get(self):

        results_array = analyze_fake_event_data()
        if results_array is None:
            print('here', 30, 'error')
            error = Error(
                "The analysis did not complete correctly."
                "The analysis went HAM and broke everything.", 500,
                "https://en.wikipedia.org/wiki/HTTP_500")
            return {"errors": error.to_json()}, 500
        else:
            return {"results": results_array}, 200
コード例 #19
0
    def birth_before_death(self):
        from datetime import date
        if not self._birthDate or not self._deathDate:
            raise AttributeError("Missing attribute")

        if (date(*self._deathDate) - date(*self._birthDate)).days > 0:
            return True
        else:
            raise Error(
                'ERROR', 'INDIVIDUAL', 'US03',
                self.get_lineNum()['BIRT'],
                f" Individual's Birthday {self.get_birthDate()} is after individual's death date {self.get_deathDate()}"
            )
コード例 #20
0
 def correct_gender_for_role(self):
     """
     throw error when missing husband/wife or missing gender of husband/wife
     :return: boolean from compare the string of husband and wife gender
     """
     if (not self._husband or not self._wife): raise AttributeError("missing husband or wife")
     if (not self._husband.get_gender() or not self._wife.get_gender()): raise AttributeError(
         "missing gender of husband or wife")
     if self._husband.get_gender() == "M" and self._wife.get_gender() == "F":
         return True
     else:raise Error ('ERROR', 'FAMILY', 'US21', self.get_lineNum()["FAM ID"],
                   f"Family {self.get_id()} 's husband {self.get_husband().get_id()} 's gender {self.get_husband().get_gender()} is incorrect "
                   f"or wife {self.get_wife().get_id()} 's gender {self.get_wife().get_gender()} is incorrect.")
コード例 #21
0
        def dfs(family, last_name):
            flag = True
            for child in family.get_children():
                if child.get_gender() == None: raise AttributeError("child's gender is not set yet")

                if child.get_gender() == "F": continue
                if not child.get_name(): raise AttributeError("Child's name is missing")
                if child.get_name().split('/')[1] != last_name:
                    #return False
                    raise Error('ERROR', 'FAMILY', 'US16', child.get_lineNum()['NAME'], f"Male Child's last name {child.get_name().split('/')[1]} doesn't match family last name {last_name}")
                for fam in child.get_family():
                    flag = dfs(fam, check_last_name) and flag
            return flag
コード例 #22
0
 def dfs(indi):
     # print(indi.get_id())
     result = True
     for family in indi.get_family():
         for child in family.get_children():
             if child in spouse:
                 #return False
                 raise Error(
                     'ERROR', 'INDIVIDUAL', 'US17',
                     child.get_lineNum()['INDI ID'],
                     f"Parent is married to a descendant{child.get_id()}"
                 )
             result = dfs(child) and result
     return result
コード例 #23
0
 def siblings_spacing(self):
     from datetime import date
     threshold = [1, 240]  # 8 month is ambiguous, let's just assume 8*30=240 days
     n = len(self.get_children())
     if n < 2: return True
     sumOfDifference = 0
     for i in range(n - 1):
         timedelta = date(*self.get_children()[i].get_birthDate()) - date(
             *self.get_children()[i + 1].get_birthDate())
         sumOfDifference += abs(timedelta.days)
     if not (threshold[0] < sumOfDifference // (n - 1) < threshold[1]):
         return True
     else: raise Error('ERROR', 'FAMILY', 'US13', self.get_lineNum()["FAM ID"],
                   f"The birth date spacing of siblings is greater than 2 days and less than 8 month")
コード例 #24
0
 def unique_name_and_birth_date(self):
     dic = set()
     for indi in self._individuals.values():
         if indi.get_birthDate():
             key = indi.get_name().replace("/", "") + "a".join(
                 list(map(str, indi.get_birthDate())))
             # print(key)
             if key not in dic:
                 dic.add(indi)
             else:
                 #return False
                 raise Error(
                     'ANOMALY', 'GEDCOM', 'US023',
                     indi.get_lineNum()['INDI ID'],
                     f"Individual{indi.get_id()} appears multiple times in the GEDCOM file"
                 )
     return True
コード例 #25
0
    def unique_first_names_in_families(self):
        for _, family in self._families:
            check_list = []
            for child in family.get_children():
                if not child.get_name() or not child.get_birthDate():
                    raise AttributeError("no name or birthdate for child")
                child_info = [child.get_name(), child.get_birthDate()]
                if child_info in check_list:
                    # return False
                    raise Error(
                        'ERROR', 'GEDCOM', 'US025',
                        child.get_lineNum()['INDI ID'],
                        f"Child{child.get_id()}'s birthday{child.get_birthDate()}or name{child.get_name()} is repeated in a family"
                    )
                check_list.append(child_info)

        return True
コード例 #26
0
    def delete(self, group_id, item_id):
        errors = validate(group_id=group_id, item_id=item_id, method="GroupItemResource.delete")
        if len(errors) > 0:
            all_errors_in_json = [error.to_json() for error in errors]
            return {'errors': all_errors_in_json}, 500

        item_group = ItemGroupModel.find_by_item_id_and_group_id(item_id, group_id)
        item_group.delete_from_db()
        item_group = ItemGroupModel.find_by_item_id_and_group_id(item_id, group_id)
        if item_group is not None:
            errors.append(Error("An unexpected error occurred item was not removed from group.",
                                "ItemGroupModel.find_by_item_id_and_group_id({}, {}) did not return None".format(item_id, group_id),
                                500,
                                "https://en.wikipedia.org/wiki/HTTP_500"))
        else:
            group = GroupModel.find_by_id(group_id)
            return group.to_json(), 200
コード例 #27
0
 def birth_before_marriage(self):
     from datetime import date
     if not self._birthDate or not self._family:
         raise AttributeError(
             "Missing self birthday or family marriage date")
     # if not self._parentFamily.get_marriedDate(): raise AttributeError("Missing attribute")
     for family in self.get_family():
         if not family.get_marriedDate():
             raise AttributeError("Missing attribute")
         timedelta = date(*family.get_marriedDate()) - date(
             *self._birthDate)
         if (timedelta.days <= 0):
             #return False
             raise Error(
                 'ERROR', 'INDIVIDUAL', 'US02',
                 self.get_lineNum()['BIRT'],
                 f" Individual's Birthday {self.get_birthDate()} is after marriage date of Family {family.get_marriedDate()}"
             )
     return True
コード例 #28
0
    def parents_not_too_old(self):
        if not self._husband or not self._wife: raise AttributeError("missing husband or wife")

        if not self._husband.get_age() or not self._wife.get_age(): raise AttributeError(
            "missing age for husband or wife")

        if not self._husband.get_age() or not self._wife.get_age(): raise AttributeError(
            "missing age for husband or wife")

        wife_age = self._wife.get_age()
        husband_age = self._husband.get_age()
        for child in self._children:
            if not child.get_age(): raise AttributeError("missing child age")
            wife_diff = wife_age - child.get_age()
            husband_diff = husband_age - child.get_age()
            if wife_diff >= 60 or husband_diff >= 80:
                raise Error('ANOMALY', 'FAMILY', 'US12', self.get_lineNum()["FAM ID"],
                            f"Family Mother's age {wife_age} exceeds child's age {child.get_age()} by 60 or Father's age {husband_age} exceeds child's age by 80")
                # return False
        return True
コード例 #29
0
    def test_error(self):

        raise Error("123", 1, 2, 3, 4)
コード例 #30
0
    def aunts_and_uncles(self):
        if (not self._parentFamily): raise AttributeError("missing value")
        if (not self._parentFamily.get_husband()
                or not self._parentFamily.get_wife()):
            raise AttributeError("missing value")
        if (not self._parentFamily.get_husband().get_parent_family()
                or not self._parentFamily.get_wife().get_parent_family()):
            raise AttributeError("missing value")

        dad_grand_family = self._parentFamily.get_husband().get_parent_family()
        mom_grand_family = self._parentFamily.get_wife().get_parent_family()

        for dad_side_aunt_uncle in dad_grand_family.get_children():
            if (dad_side_aunt_uncle == self.get_parent_family().get_husband()):
                continue
            check_id = dad_side_aunt_uncle.get_id()
            for dad_side_family in dad_side_aunt_uncle.get_family():
                if (not dad_side_family.get_husband()
                        or not dad_side_family.get_wife()):
                    raise AttributeError("missing value")
                uncle_id = dad_side_family.get_husband().get_id()
                aunt_id = dad_side_family.get_wife().get_id()
                if (uncle_id == aunt_id):
                    #return False
                    raise Error(
                        'ERROR', 'INDIVIDUAL', 'US20',
                        dad_side_family.get_husband().get_lineNum()['INDI ID'],
                        f" Individual's Aunt{aunt_id} and Uncle{uncle_id} has the same ID"
                    )
                for each_child in dad_side_family.get_children():
                    if (uncle_id == each_child.get_id()
                            or aunt_id == each_child.get_id()):
                        #return False
                        raise Error(
                            'ERROR', 'INDIVIDUAL', 'US20',
                            dad_side_family.get_husband().get_lineNum()
                            ['INDI ID'],
                            f" Individual's Aunt{aunt_id} or Uncle{uncle_id} is married to their child {each_child.get_id()}"
                        )
        for mom_side_aunt_uncle in mom_grand_family.get_children():
            if (mom_side_aunt_uncle == self.get_parent_family().get_wife()):
                continue
            for mom_side_family in mom_side_aunt_uncle.get_family():
                if (not mom_side_family.get_husband()
                        or not mom_side_family.get_wife()):
                    raise AttributeError("missing value")
                uncle_id = mom_side_family.get_husband().get_id()
                aunt_id = mom_side_family.get_wife().get_id()
                if (uncle_id == aunt_id):
                    #return False
                    raise Error(
                        'ERROR', 'INDIVIDUAL', 'US20',
                        mom_side_family.get_husband().get_lineNum()['INDI ID'],
                        f" Individual's Aunt{aunt_id} and Uncle{uncle_id} has the same ID"
                    )
                for each_child in mom_side_family.get_children():
                    if (uncle_id == each_child.get_id()
                            or aunt_id == each_child.get_id()):
                        #return False
                        raise Error(
                            'ERROR', 'INDIVIDUAL', 'US20',
                            mom_side_family.get_husband().get_lineNum()
                            ['INDI ID'],
                            f" Individual's Aunt{aunt_id} or Uncle{uncle_id} is married to their child {each_child.get_id()}"
                        )

        return True