def testInheritanceCycleAcrossNamepsaces(self):
        type1 = entity_type_lib.EntityType(filepath='path/to/ANIMAL/mammal',
                                           typename='dog',
                                           description='canine animal',
                                           local_field_tuples=_F(['/woof']),
                                           parents=['ANIMAL/wolf'])

        type2 = entity_type_lib.EntityType(filepath='path/to/ANIMAL/mammal',
                                           typename='wolf',
                                           description='canine animal',
                                           local_field_tuples=_F(['/growl']),
                                           parents=['FUZZY_ANIMAL/dingo'])

        type3 = entity_type_lib.EntityType(
            filepath='path/to/FUZZY_ANIMAL/mammal',
            typename='dingo',
            description='canine animal',
            local_field_tuples=_F(['/wag']),
            parents=['ANIMAL/dog'])

        namespace = entity_type_lib.TypeNamespace(namespace='ANIMAL')
        namespace.InsertType(type1)
        namespace.InsertType(type2)
        namespace2 = entity_type_lib.TypeNamespace(namespace='FUZZY_ANIMAL')
        namespace2.InsertType(type3)
        namespace_validate = (namespace_validator.NamespaceValidator(
            [namespace, namespace2]))

        self.assertTrue(
            namespace_validate.HasFindingTypes(
                [findings_lib.InheritanceCycleError]))
    def testInheritTypesFromDifferentNamespace(self):
        type1 = entity_type_lib.EntityType(filepath='path/to/ANIMAL/mammal',
                                           typename='dog',
                                           description='canine animal',
                                           local_field_tuples=_F(
                                               ['/woof', '/howl']))

        type2 = entity_type_lib.EntityType(filepath='path/to/INSECT/fly',
                                           typename='moth',
                                           description='flying insect.',
                                           local_field_tuples=_F(['/wings']),
                                           parents=['ANIMAL/dog'])

        type_namespace_1 = entity_type_lib.TypeNamespace(namespace='ANIMAL')
        type_namespace_1.InsertType(type1)
        type_namespace_2 = entity_type_lib.TypeNamespace(namespace='INSECT')
        type_namespace_2.InsertType(type2)
        namespace_validate = (namespace_validator.NamespaceValidator(
            [type_namespace_1, type_namespace_2]))

        self.assertFalse(namespace_validate.GetFindings())

        expanded_type_namespace_1 = namespace_validate.type_namespaces_map.get(
            type_namespace_1.namespace)
        expanded_type_namespace_2 = namespace_validate.type_namespaces_map.get(
            type_namespace_2.namespace)

        type1_expanded = expanded_type_namespace_1.valid_types_map.get(
            type1.typename)
        type2_expanded = expanded_type_namespace_2.valid_types_map.get(
            type2.typename)

        self.assertEmpty(type1_expanded.inherited_field_names)
        self.assertLen(type2_expanded.inherited_field_names, 2)
    def testGetFieldFromConfigText(self):
        entity_type = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/mammal',
            description='canine animal',
            local_field_tuples=_FS(['HAPPY/wag', '/woof', 'ANIMALS/fuzzy']),
            inherited_fields_expanded=True,
            namespace=entity_type_lib.TypeNamespace('ANIMALS'))
        self.assertEqual(
            'fuzzy',
            entity_type.GetFieldFromConfigText('fuzzy').field.field)
        self.assertEqual(
            'fuzzy',
            entity_type.GetFieldFromConfigText('ANIMALS/fuzzy').field.field)
        self.assertEqual(
            'wag',
            entity_type.GetFieldFromConfigText('HAPPY/wag').field.field)
        self.assertEqual(
            'woof',
            entity_type.GetFieldFromConfigText('woof').field.field)
        self.assertEqual(
            'woof',
            entity_type.GetFieldFromConfigText('/woof').field.field)

        self.assertIsNone(entity_type.GetFieldFromConfigText('/wag'))
        self.assertIsNone(entity_type.GetFieldFromConfigText('wag'))
    def testDuplicateLocalFieldSets(self):
        type1 = entity_type_lib.EntityType(filepath='path/to/ANIMAL/mammal',
                                           typename='dog',
                                           description='canine animal',
                                           local_field_tuples=_F(
                                               ['/woof', '/howl']))

        type2 = entity_type_lib.EntityType(filepath='path/to/ANIMAL/mammal',
                                           typename='wolf',
                                           description='canine animal',
                                           local_field_tuples=_F(
                                               ['/woof', '/howl']))
        type2.inherited_field_names = ({'/bark': _F1('/bark', optional=True)})

        type_namespace = entity_type_lib.TypeNamespace(namespace='ANIMAL')
        type_namespace.InsertType(type1)
        type_namespace.InsertType(type2)

        namespace_validator.NamespaceValidator([type_namespace])

        self.assertTrue(
            type1.HasFindingTypes(
                [findings_lib.DuplicateLocalFieldSetsWarning]))
        self.assertTrue(
            type2.HasFindingTypes(
                [findings_lib.DuplicateLocalFieldSetsWarning]))
    def testGoodFieldIncrement(self):
        entity_type = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/mammal',
            typename='dog',
            description='canine animal',
            local_field_tuples=_F(['/woof', '/woof_1']))

        type_namespace = entity_type_lib.TypeNamespace(namespace='ANIMAL')
        type_namespace.InsertType(entity_type)
        namespace_validate = (namespace_validator.NamespaceValidator(
            [type_namespace]))

        self.assertTrue(namespace_validate.IsValid())
    def testInheritTypesFromDifferentNamespaceError(self):
        type1 = entity_type_lib.EntityType(filepath='path/to/ANIMAL/mammal',
                                           typename='dog',
                                           description='canine animal',
                                           local_field_tuples=_F(
                                               ['/woof', '/howl']))

        type2 = entity_type_lib.EntityType(filepath='path/to/INSECT/fly',
                                           typename='moth',
                                           description='flying insect.',
                                           local_field_tuples=_F(['/wings']),
                                           parents=['ANIMALLLLL/dog'])

        type_namespace_1 = entity_type_lib.TypeNamespace(namespace='ANIMAL')
        type_namespace_1.InsertType(type1)
        type_namespace_2 = entity_type_lib.TypeNamespace(namespace='INSECT')
        type_namespace_2.InsertType(type2)
        namespace_validate = (namespace_validator.NamespaceValidator(
            [type_namespace_1, type_namespace_2]))

        self.assertTrue(
            namespace_validate.HasFindingTypes(
                [findings_lib.NonexistentParentError]))
    def testGoodPassthroughType(self):
        passthrough_type = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/gateway',
            typename='dog',
            description='a gateway to dogs',
            allow_undefined_fields=True,
            local_field_tuples=_F(['/woof_1', '/woof_2', '/woof_3']))

        type_namespace = entity_type_lib.TypeNamespace(namespace='ANIMAL')
        type_namespace.InsertType(passthrough_type)
        namespace_validate = (namespace_validator.NamespaceValidator(
            [type_namespace]))

        self.assertTrue(namespace_validate.IsValid())
    def testHasFieldAsWritten(self):
        entity_type = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/mammal',
            description='canine animal',
            local_field_tuples=_FS(['HAPPY/wag', '/woof', 'ANIMALS/fuzzy']),
            inherited_fields_expanded=True,
            namespace=entity_type_lib.TypeNamespace('ANIMALS'))

        self.assertTrue(entity_type.HasFieldAsWritten('fuzzy'))
        self.assertTrue(entity_type.HasFieldAsWritten('ANIMALS/fuzzy'))
        self.assertTrue(entity_type.HasFieldAsWritten('HAPPY/wag'))
        self.assertTrue(entity_type.HasFieldAsWritten('woof'))
        self.assertTrue(entity_type.HasFieldAsWritten('/woof'))

        self.assertFalse(entity_type.HasFieldAsWritten('/wag'))
        self.assertFalse(entity_type.HasFieldAsWritten('wag'))
    def testNonexistentParent(self):
        entity_type = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/mammal',
            typename='dog',
            description='canine animal',
            local_field_tuples=_F(['/woof']),
            parents=[('/nonexistent')])

        type_namespace = entity_type_lib.TypeNamespace(namespace='ANIMAL')
        type_namespace.InsertType(entity_type)
        namespace_validate = (namespace_validator.NamespaceValidator(
            [type_namespace]))

        self.assertTrue(
            namespace_validate.HasFindingTypes(
                [findings_lib.NonexistentParentError]))
    def testTypesWithEmptyFields(self):
        type1 = entity_type_lib.EntityType(filepath='path/to/ANIMAL/mammal',
                                           typename='dog',
                                           description='canine animal')

        type2 = entity_type_lib.EntityType(filepath='path/to/ANIMAL/mammal',
                                           typename='wolf',
                                           description='canine animal')

        type_namespace = entity_type_lib.TypeNamespace(namespace='ANIMAL')
        type_namespace.InsertType(type1)
        type_namespace.InsertType(type2)

        namespace_validator.NamespaceValidator([type_namespace])

        self.assertFalse(
            type1.HasFindingTypes(
                [findings_lib.DuplicateLocalFieldSetsWarning]))
        self.assertFalse(
            type2.HasFindingTypes(
                [findings_lib.DuplicateLocalFieldSetsWarning]))
    def testSetsInheritedOptionality(self):
        type1 = entity_type_lib.EntityType(filepath='path/to/ANIMAL/mammal',
                                           typename='dog',
                                           description='canine animal',
                                           local_field_tuples=[
                                               _F1('/woof', optional=True),
                                               _F1('/growl', optional=True)
                                           ],
                                           parents=[])

        type2 = entity_type_lib.EntityType(filepath='path/to/ANIMAL/mammal',
                                           typename='wolf',
                                           description='canine animal',
                                           local_field_tuples=[
                                               _F1('/woof', optional=True),
                                               _F1('/growl', optional=False)
                                           ],
                                           parents=[])

        type3 = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/mammal',
            typename='dingo',
            description='canine animal',
            local_field_tuples=[_F1('/wag', optional=False)],
            parents=['ANIMAL/dog', 'ANIMAL/wolf'])

        type_namespace_1 = entity_type_lib.TypeNamespace(namespace='ANIMAL')
        type_namespace_1.InsertType(type1)
        type_namespace_1.InsertType(type2)
        type_namespace_1.InsertType(type3)

        namespace_validate = (namespace_validator.NamespaceValidator(
            [type_namespace_1]))

        self.assertTrue(namespace_validate.IsValid())
        field_map = type3.GetAllFields()
        self.assertFalse(field_map['/growl'].optional)
        self.assertTrue(field_map['/woof'].optional)
        self.assertFalse(field_map['/wag'].optional)
    def testInheritingFromPassthroughIsError(self):
        passthrough_type = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/gateway',
            typename='dog',
            description='a gateway to dogs',
            allow_undefined_fields=True)
        entity_type = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/mammal',
            typename='dingo',
            description='canine animal',
            local_field_tuples=_F(['/woof']),
            parents=['ANIMAL/dog'])

        type_namespace = entity_type_lib.TypeNamespace(namespace='ANIMAL')
        type_namespace.InsertType(passthrough_type)
        type_namespace.InsertType(entity_type)
        namespace_validate = (namespace_validator.NamespaceValidator(
            [type_namespace]))

        self.assertTrue(
            namespace_validate.HasFindingTypes(
                [findings_lib.PassthroughParentError]))
    def setUp(self):
        super(NamespaceValidatorTest, self).setUp()
        # Create a list of good TypeNamespace objects
        self.good_type1 = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/mammal',
            typename='animal',
            description='member of the animal kingdom',
            local_field_tuples=_F(['/animalia']))

        self.good_type2 = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/mammal',
            typename='dog',
            description='canine animal',
            local_field_tuples=_F(['/woof', '/wag']),
            parents=['ANIMAL/animal'])

        self.good_type3 = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/mammal',
            typename='puppy',
            description='baby dog',
            local_field_tuples=_F(['/cute']),
            parents=['ANIMAL/dog', 'ANIMAL/animal', 'ANIMAL/baby'])

        self.good_type4 = entity_type_lib.EntityType(
            filepath='path/to/ANIMAL/mammal',
            typename='baby',
            description='young animal',
            local_field_tuples=_F(['/young']))

        self.type_namespace = entity_type_lib.TypeNamespace(namespace='ANIMAL')
        self.type_namespace.InsertType(self.good_type1)
        self.type_namespace.InsertType(self.good_type2)
        self.type_namespace.InsertType(self.good_type3)
        self.type_namespace.InsertType(self.good_type4)

        self.validate_good = (namespace_validator.NamespaceValidator(
            [self.type_namespace]))