add new entity union and validation

This commit is contained in:
Na Zhang 2020-08-29 22:00:22 -07:00 committed by John Plaisted
parent a3a892f5ec
commit 5fcbd4cdc7
4 changed files with 69 additions and 0 deletions

View File

@ -531,4 +531,28 @@ public class ModelUtils {
public static boolean isCommonAspect(@Nonnull Class<? extends RecordTemplate> clazz) {
return clazz.getPackage().getName().startsWith("com.linkedin.common");
}
/**
* Creates an entity union with a specific entity set.
*
* @param entityUnionClass the type of entity union to create
* @param entity the entity to set
* @param <ENTITY_UNION> must be a valid enity union defined in com.linkedin.metadata.entity
* @param <ENTITY> must be a supported entity in entity union
* @return the created entity union
*/
@Nonnull
public static <ENTITY_UNION extends UnionTemplate, ENTITY extends RecordTemplate> ENTITY_UNION newEntityUnion(
@Nonnull Class<ENTITY_UNION> entityUnionClass, @Nonnull ENTITY entity) {
EntityValidator.validateEntityUnionSchema(entityUnionClass);
try {
ENTITY_UNION entityUnion = entityUnionClass.newInstance();
RecordUtils.setSelectedRecordTemplateInUnion(entityUnion, entity);
return entityUnion;
} catch (InstantiationException | IllegalAccessException e) {
throw new RuntimeException(e);
}
}
}

View File

@ -4,6 +4,7 @@ import com.google.common.collect.ImmutableSet;
import com.linkedin.common.Ownership;
import com.linkedin.common.urn.Urn;
import com.linkedin.testing.EntityFoo;
import com.linkedin.testing.EntityUnion;
import com.linkedin.testing.urn.BarUrn;
import com.linkedin.data.template.RecordTemplate;
import com.linkedin.metadata.validator.InvalidSchemaException;
@ -283,4 +284,12 @@ public class ModelUtilsTest {
result = ModelUtils.isCommonAspect(Ownership.class);
assertTrue(result);
}
@Test
public void testNewEntityUnion() {
EntityFoo entityFoo = new EntityFoo().setUrn(makeFooUrn(1));
EntityUnion entityUnion = ModelUtils.newEntityUnion(EntityUnion.class, entityFoo);
assertEquals(entityUnion.getEntityFoo(), entityFoo);
}
}

View File

@ -0,0 +1,6 @@
namespace com.linkedin.testing
/**
* For unit testing
*/
typeref EntityUnion = union[EntityFoo, EntityBar]

View File

@ -1,7 +1,9 @@
package com.linkedin.metadata.validator;
import com.linkedin.data.schema.RecordDataSchema;
import com.linkedin.data.schema.UnionDataSchema;
import com.linkedin.data.template.RecordTemplate;
import com.linkedin.data.template.UnionTemplate;
import java.util.Collections;
import java.util.HashSet;
import java.util.Set;
@ -21,6 +23,10 @@ public class EntityValidator {
// A cache of validated classes
private static final Set<Class<? extends RecordTemplate>> VALIDATED = ConcurrentHashMap.newKeySet();
// A cache of validated classes
private static final Set<Class<? extends UnionTemplate>> UNION_VALIDATED = ConcurrentHashMap.newKeySet();
private EntityValidator() {
// Util class
}
@ -60,6 +66,30 @@ public class EntityValidator {
VALIDATED.add(clazz);
}
/**
* Similar to {@link #validateEntityUnionSchema(UnionDataSchema, String)} but take a {@link Class} instead and caches results.
*/
public static void validateEntityUnionSchema(@Nonnull Class<? extends UnionTemplate> clazz) {
if (UNION_VALIDATED.contains(clazz)) {
return;
}
validateEntityUnionSchema(ValidationUtils.getUnionSchema(clazz), clazz.getCanonicalName());
UNION_VALIDATED.add(clazz);
}
/**
* Validates the union of entity model defined in com.linkedin.metadata.entity.
*
* @param schema schema for the model
*/
public static void validateEntityUnionSchema(@Nonnull UnionDataSchema schema, @Nonnull String entityClassName) {
if (!ValidationUtils.isUnionWithOnlyComplexMembers(schema)) {
ValidationUtils.invalidSchema("Entity '%s' must be a union containing only record type members", entityClassName);
}
}
/**
* Checks if an entity schema is valid
*/