/** * Make the second argument the super of the first argument * * @throws GraqlQueryException if the types are different, or setting the super to be a meta-type */ public static void setSuper(SchemaConcept subConcept, SchemaConcept superConcept) { if (superConcept.isEntityType()) { subConcept.asEntityType().sup(superConcept.asEntityType()); } else if (superConcept.isRelationshipType()) { subConcept.asRelationshipType().sup(superConcept.asRelationshipType()); } else if (superConcept.isRole()) { subConcept.asRole().sup(superConcept.asRole()); } else if (superConcept.isAttributeType()) { subConcept.asAttributeType().sup(superConcept.asAttributeType()); } else if (superConcept.isRule()) { subConcept.asRule().sup(superConcept.asRule()); } else { throw GraqlQueryException.insertMetaType(subConcept.label(), superConcept); } }
/** * Create a var with the information underlying all Types * @param schemaConcept type to be mapped * @return {@link VarPattern} containing basic information about the given type */ private static VarPattern formatBase(SchemaConcept schemaConcept) { VarPattern var = var().label(schemaConcept.label()); SchemaConcept superType = schemaConcept.sup(); if (schemaConcept.sup() != null) { var = var.sub(Graql.label(superType.label())); } if(schemaConcept.isType()) { Type type = schemaConcept.asType(); var = plays(var, type); var = isAbstract(var, type); } return var; }
private static boolean mayHaveEdgeInstances(SchemaConcept concept) { return concept.isRelationshipType() && concept.isImplicit(); } }
/** * @param schemaConcept input type * @return set of all non-meta super types of the role */ public static Set<SchemaConcept> supers(SchemaConcept schemaConcept){ Set<SchemaConcept> superTypes = new HashSet<>(); SchemaConcept superType = schemaConcept.sup(); while(superType != null && !Schema.MetaSchema.isMetaLabel(superType.label())) { superTypes.add(superType); superType = superType.sup(); } return superTypes; }
private SchemaConcept putSchemaConcept() { SchemaConcept superConcept = use(SUPER_CONCEPT); Label label = use(LABEL); SchemaConcept concept; if (superConcept.isEntityType()) { concept = executor.tx().putEntityType(label); } else if (superConcept.isRelationshipType()) { concept = executor.tx().putRelationshipType(label); } else if (superConcept.isRole()) { concept = executor.tx().putRole(label); } else if (superConcept.isAttributeType()) { AttributeType attributeType = superConcept.asAttributeType(); AttributeType.DataType<?> dataType = useOrDefault(DATA_TYPE, attributeType.dataType()); concept = executor.tx().putAttributeType(label, dataType); } else if (superConcept.isRule()) { concept = executor.tx().putRule(label, use(WHEN), use(THEN)); } else { throw GraqlQueryException.insertMetaType(label, superConcept); } setSuper(concept, superConcept); return concept; }
/** * Thrown when setting {@code superType} as the super type of {@code type} and a loop is created */ public static GraknTxOperationException loopCreated(SchemaConcept type, SchemaConcept superElement){ return create(ErrorMessage.SUPER_LOOP_DETECTED.getMessage(type.label(), superElement.label())); }
/** * Map a Type to the Graql string representation * @param schemaConcept type to be mapped * @return Graql var equivalent to the given type */ public static VarPattern map(SchemaConcept schemaConcept) { VarPattern mapped = formatBase(schemaConcept); if (schemaConcept.isRelationshipType()) { mapped = map(mapped, schemaConcept.asRelationshipType()); } else if (schemaConcept.isAttributeType()) { mapped = map(mapped, schemaConcept.asAttributeType()); } return mapped; }
@Override public Set<String> validateOntologically() { SchemaConcept type = getSchemaConcept(); Set<String> errors = new HashSet<>(); if (type == null) return errors; if (!type.isAttributeType()){ errors.add(ErrorMessage.VALIDATION_RULE_INVALID_ATTRIBUTE_TYPE.getMessage(type.label())); return errors; } Type ownerType = getParentQuery().getVarTypeMap().get(getVarName()); if (ownerType != null && ownerType.attributes().noneMatch(rt -> rt.equals(type.asAttributeType()))){ errors.add(ErrorMessage.VALIDATION_RULE_ATTRIBUTE_OWNER_CANNOT_HAVE_ATTRIBUTE.getMessage(type.label(), ownerType.label())); } return errors; }
@Override public Set<String> validateOntologically() { Set<String> errors = new HashSet<>(); SchemaConcept type = getSchemaConcept(); if (type != null && !type.isRelationshipType()){ errors.add(ErrorMessage.VALIDATION_RULE_INVALID_RELATION_TYPE.getMessage(type.label())); return errors; } //check role-type compatibility Map<Var, Type> varTypeMap = getParentQuery().getVarTypeMap(); for (Map.Entry<Role, Collection<Var>> e : getRoleVarMap().asMap().entrySet() ){ Role role = e.getKey(); if (!Schema.MetaSchema.isMetaLabel(role.label())) { //check whether this role can be played in this relation if (type != null && type.asRelationshipType().roles().noneMatch(r -> r.equals(role))) { errors.add(ErrorMessage.VALIDATION_RULE_ROLE_CANNOT_BE_PLAYED.getMessage(role.label(), type.label())); } //check whether the role player's type allows playing this role for (Var player : e.getValue()) { Type playerType = varTypeMap.get(player); if (playerType != null && playerType.playing().noneMatch(plays -> plays.equals(role))) { errors.add(ErrorMessage.VALIDATION_RULE_TYPE_CANNOT_PLAY_ROLE.getMessage(playerType.label(), role.label(), type == null? "" : type.label())); } } } } return errors; }
private Set<SchemaConcept> getTypes(SchemaConcept type, boolean direct) { Set<SchemaConcept> types = direct ? Sets.newHashSet(type) : type.subs().collect(Collectors.toSet()); return type.isImplicit()? types.stream().flatMap(t -> Stream.of(t, tx.getSchemaConcept(Schema.ImplicitType.explicitLabel(t.label())))).collect(Collectors.toSet()): types; }
private static Map<Var, Type> getLabelVarTypeMap(EmbeddedGraknTx<?> tx, Set<Fragment> allFragments) { Map<Var, Type> labelVarTypeMap = new HashMap<>(); allFragments.stream() .filter(LabelFragment.class::isInstance) .forEach(fragment -> { // TODO: labels() should return ONE label instead of a set SchemaConcept schemaConcept = tx.getSchemaConcept( Iterators.getOnlyElement(((LabelFragment) fragment).labels().iterator())); if (schemaConcept != null && !schemaConcept.isRole() && !schemaConcept.isRule()) { labelVarTypeMap.put(fragment.start(), schemaConcept.asType()); } }); return labelVarTypeMap; }
/** * Copies the {@link SchemaConcept} and it's subs into the {@link TxCache}. * This is important as lookups for {@link SchemaConcept}s based on {@link Label} depend on this caching. * * @param schemaConcept the {@link SchemaConcept} to be copied into the {@link TxCache} */ private void copyToCache(SchemaConcept schemaConcept) { schemaConcept.subs().forEach(concept -> { getGlobalCache().cacheLabel(concept.label(), concept.labelId()); getGlobalCache().cacheType(concept.label(), concept); }); }
@Nullable @Override public <V> AttributeType<V> getAttributeType(String label) { SchemaConcept concept = getSchemaConcept(Label.of(label)); if (concept == null || !concept.isAttributeType()) return null; return concept.asAttributeType(); }
@Nullable @Override public RelationshipType getRelationshipType(String label) { SchemaConcept concept = getSchemaConcept(Label.of(label)); if (concept == null || !concept.isRelationshipType()) return null; return concept.asRelationshipType(); }
@Override public void checkValidProperty(GraknTx graph, VarPatternAdmin var) throws GraqlQueryException { Set<Label> roleTypes = relationPlayers().stream() .map(RelationPlayer::getRole).flatMap(CommonUtil::optionalToStream) .map(VarPatternAdmin::getTypeLabel).flatMap(CommonUtil::optionalToStream) .collect(toSet()); Optional<Label> maybeLabel = var.getProperty(IsaProperty.class).map(IsaProperty::type).flatMap(VarPatternAdmin::getTypeLabel); maybeLabel.ifPresent(label -> { SchemaConcept schemaConcept = graph.getSchemaConcept(label); if (schemaConcept == null || !schemaConcept.isRelationshipType()) { throw GraqlQueryException.notARelationType(label); } }); // Check all role types exist roleTypes.forEach(roleId -> { SchemaConcept schemaConcept = graph.getSchemaConcept(roleId); if (schemaConcept == null || !schemaConcept.isRole()) { throw GraqlQueryException.notARoleType(roleId); } }); }
@Override public RelationshipAtom toRelationshipAtom(){ SchemaConcept type = getSchemaConcept(); if (type == null) throw GraqlQueryException.illegalAtomConversion(this, RelationshipAtom.class); GraknTx tx = getParentQuery().tx(); Label typeLabel = Schema.ImplicitType.HAS.getLabel(type.label()); return RelationshipAtom.create( Graql.var() .rel(Schema.ImplicitType.HAS_OWNER.getLabel(type.label()).getValue(), getVarName()) .rel(Schema.ImplicitType.HAS_VALUE.getLabel(type.label()).getValue(), getPredicateVariable()) .isa(typeLabel.getValue()) .admin(), getPredicateVariable(), tx.getSchemaConcept(typeLabel).id(), getParentQuery() ); }
@Nullable @Override public EntityType getEntityType(String label) { SchemaConcept concept = getSchemaConcept(Label.of(label)); if (concept == null || !concept.isEntityType()) return null; return concept.asEntityType(); }
/** * Caches a concept so it does not have to be rebuilt later. * * @param concept The concept to be cached. */ public void cacheConcept(Concept concept){ conceptCache.put(concept.id(), concept); if(concept.isSchemaConcept()){ SchemaConcept schemaConcept = concept.asSchemaConcept(); schemaConceptCache.put(schemaConcept.label(), schemaConcept); labelCache.put(schemaConcept.label(), schemaConcept.labelId()); } }