Add entity type constraint check
This commit is contained in:
parent
e2ae09f5be
commit
1910833ad8
@ -236,6 +236,10 @@
|
||||
"no-unit-provided": {
|
||||
"title": "Unit missing for {property_entity}",
|
||||
"body": "Values such as <span class=\"wb-issue-preformat\">{example_value}</span> on {example_item_entity} are expected to have units."
|
||||
},
|
||||
"invalid-entity-type": {
|
||||
"title": "{property_entity} used on items",
|
||||
"body": "Uses of {property_entity} on items such as {example_entity} are invalid."
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -129,4 +129,9 @@ public interface ConstraintFetcher {
|
||||
* Returns the allowed units for this property. If empty, no unit is allowed. If null, any unit is allowed.
|
||||
*/
|
||||
Set<ItemIdValue> allowedUnits(PropertyIdValue pid);
|
||||
|
||||
/**
|
||||
* Can this property be used on items?
|
||||
*/
|
||||
boolean usableOnItems(PropertyIdValue pid);
|
||||
}
|
||||
|
@ -30,6 +30,7 @@ import java.util.stream.Collectors;
|
||||
|
||||
import org.openrefine.wikidata.qa.scrutinizers.DistinctValuesScrutinizer;
|
||||
import org.openrefine.wikidata.qa.scrutinizers.EditScrutinizer;
|
||||
import org.openrefine.wikidata.qa.scrutinizers.EntityTypeScrutinizer;
|
||||
import org.openrefine.wikidata.qa.scrutinizers.FormatScrutinizer;
|
||||
import org.openrefine.wikidata.qa.scrutinizers.InverseConstraintScrutinizer;
|
||||
import org.openrefine.wikidata.qa.scrutinizers.NewItemScrutinizer;
|
||||
@ -77,6 +78,7 @@ public class EditInspector {
|
||||
register(new WhitespaceScrutinizer());
|
||||
register(new QuantityScrutinizer());
|
||||
register(new RestrictedValuesScrutinizer());
|
||||
register(new EntityTypeScrutinizer());
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -31,6 +31,7 @@ import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import org.openrefine.wikidata.utils.EntityCache;
|
||||
import org.wikidata.wdtk.datamodel.helpers.Datamodel;
|
||||
import org.wikidata.wdtk.datamodel.interfaces.EntityIdValue;
|
||||
import org.wikidata.wdtk.datamodel.interfaces.ItemIdValue;
|
||||
import org.wikidata.wdtk.datamodel.interfaces.PropertyDocument;
|
||||
@ -88,6 +89,10 @@ public class WikidataConstraintFetcher implements ConstraintFetcher {
|
||||
public static String ALLOWED_UNITS_CONSTRAINT_QID = "Q21514353";
|
||||
public static String ALLOWED_UNITS_CONSTRAINT_PID = "P2305";
|
||||
|
||||
public static String ALLOWED_ENTITY_TYPES_QID = "Q52004125";
|
||||
public static String ALLOWED_ITEM_TYPE_QID = "Q29934200";
|
||||
public static String ALLOWED_ENTITY_TYPES_PID = "P2305";
|
||||
|
||||
|
||||
// The following constraints still need to be implemented:
|
||||
|
||||
@ -224,6 +229,16 @@ public class WikidataConstraintFetcher implements ConstraintFetcher {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean usableOnItems(PropertyIdValue pid) {
|
||||
List<SnakGroup> constraint = getSingleConstraint(pid, ALLOWED_ENTITY_TYPES_QID);
|
||||
if (constraint != null) {
|
||||
return findValues(constraint, ALLOWED_ENTITY_TYPES_PID).contains(
|
||||
Datamodel.makeWikidataItemIdValue(ALLOWED_ITEM_TYPE_QID));
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a single constraint for a particular type and a property, or null if
|
||||
* there is no such constraint
|
||||
|
@ -0,0 +1,22 @@
|
||||
package org.openrefine.wikidata.qa.scrutinizers;
|
||||
|
||||
import org.openrefine.wikidata.qa.QAWarning;
|
||||
import org.wikidata.wdtk.datamodel.interfaces.EntityIdValue;
|
||||
import org.wikidata.wdtk.datamodel.interfaces.PropertyIdValue;
|
||||
import org.wikidata.wdtk.datamodel.interfaces.Snak;
|
||||
|
||||
|
||||
public class EntityTypeScrutinizer extends SnakScrutinizer {
|
||||
|
||||
public final static String type = "invalid-entity-type";
|
||||
|
||||
@Override
|
||||
public void scrutinize(Snak snak, EntityIdValue entityId, boolean added) {
|
||||
PropertyIdValue pid = snak.getPropertyId();
|
||||
if(!_fetcher.usableOnItems(pid)) {
|
||||
QAWarning issue = new QAWarning(type, null, QAWarning.Severity.WARNING, 1);
|
||||
issue.setProperty("example_entity", entityId);
|
||||
addIssue(issue);
|
||||
}
|
||||
}
|
||||
}
|
@ -57,6 +57,8 @@ public class MockConstraintFetcher implements ConstraintFetcher {
|
||||
public static PropertyIdValue noBoundsPid = Datamodel.makeWikidataPropertyIdValue("P8932");
|
||||
public static PropertyIdValue integerPid = Datamodel.makeWikidataPropertyIdValue("P389");
|
||||
|
||||
public static PropertyIdValue propertyOnlyPid = Datamodel.makeWikidataPropertyIdValue("P372");
|
||||
|
||||
@Override
|
||||
public String getFormatRegex(PropertyIdValue pid) {
|
||||
return "[1-9]\\d+";
|
||||
@ -154,4 +156,9 @@ public class MockConstraintFetcher implements ConstraintFetcher {
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean usableOnItems(PropertyIdValue pid) {
|
||||
return !propertyOnlyPid.equals(pid);
|
||||
}
|
||||
}
|
||||
|
@ -0,0 +1,29 @@
|
||||
package org.openrefine.wikidata.qa.scrutinizers;
|
||||
|
||||
import org.openrefine.wikidata.qa.MockConstraintFetcher;
|
||||
import org.openrefine.wikidata.testing.TestingData;
|
||||
import org.testng.annotations.Test;
|
||||
import org.wikidata.wdtk.datamodel.helpers.Datamodel;
|
||||
import org.wikidata.wdtk.datamodel.interfaces.ItemIdValue;
|
||||
|
||||
public class EntityTypeScrutinizerTest extends StatementScrutinizerTest {
|
||||
|
||||
private static ItemIdValue qid = Datamodel.makeWikidataItemIdValue("Q343");
|
||||
|
||||
@Override
|
||||
public EditScrutinizer getScrutinizer() {
|
||||
return new EntityTypeScrutinizer();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testAllowed() {
|
||||
scrutinize(TestingData.generateStatement(qid, qid));
|
||||
assertNoWarningRaised();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testDisallowed() {
|
||||
scrutinize(TestingData.generateStatement(qid, MockConstraintFetcher.propertyOnlyPid, qid));
|
||||
assertWarningsRaised(EntityTypeScrutinizer.type);
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user