use of org.geotoolkit.feature.ViewMapper in project geotoolkit by Geomatys.
the class GenericQueryFeatureIterator method wrap.
public static FeatureReader wrap(FeatureReader reader, final Query remainingParameters) throws DataStoreException {
final long start = remainingParameters.getOffset();
final long max = remainingParameters.getLimit().orElse(-1);
Filter filter = remainingParameters.getSelection();
if (filter == null)
filter = Filter.include();
final String[] properties = remainingParameters.getPropertyNames();
final SortProperty[] sorts = QueryUtilities.getSortProperties(remainingParameters.getSortBy());
final double[] resampling = remainingParameters.getResolution();
final Hints hints = remainingParameters.getHints();
// that may cause out of memory errors.
if (sorts != null && sorts.length != 0) {
reader = FeatureStreams.sort(reader, sorts);
}
// we must keep the filter first since it impacts the start index and max feature
if (filter != null && filter != Filter.include()) {
if (filter == Filter.exclude()) {
// filter that exclude everything, use optimzed reader
reader = FeatureStreams.emptyReader(reader.getFeatureType());
// close original reader
reader.close();
} else {
reader = FeatureStreams.filter(reader, filter);
}
}
// wrap start index -----------------------------------------------------
if (start > 0) {
reader = FeatureStreams.skip(reader, (int) start);
}
// wrap max -------------------------------------------------------------
if (max != -1) {
if (max == 0) {
// use an optimized reader
reader = FeatureStreams.emptyReader(reader.getFeatureType());
// close original reader
reader.close();
} else {
reader = FeatureStreams.limit(reader, (int) max);
}
}
// wrap properties -----------------------------------------------------
final FeatureType original = reader.getFeatureType();
if (properties != null && !FeatureTypeExt.isAllProperties(original, properties)) {
try {
reader = FeatureStreams.decorate(reader, new ViewMapper(original, properties), hints);
} catch (MismatchedFeatureException | IllegalStateException ex) {
throw new DataStoreException(ex);
}
}
// wrap resampling ------------------------------------------------------
if (resampling != null) {
final GeometryScaleTransformer trs = new GeometryScaleTransformer(resampling[0], resampling[1]);
final TransformMapper ttype = new TransformMapper(reader.getFeatureType(), trs);
reader = FeatureStreams.decorate(reader, ttype, hints);
}
return reader;
}
use of org.geotoolkit.feature.ViewMapper in project geotoolkit by Geomatys.
the class ViewFeatureTypeTest method filterOperationTest.
@Test
public void filterOperationTest() {
final FeatureTypeBuilder ftb = new FeatureTypeBuilder();
ftb.setName("test");
final AttributeType<String> attString = ftb.addAttribute(String.class).setName("attString").build();
ftb.addProperty(FeatureOperations.link(Collections.singletonMap("name", "attRef"), attString));
final FeatureType baseType = ftb.build();
// test view type
final ViewMapper viewType = new ViewMapper(baseType, "attRef");
final Collection<? extends PropertyType> properties = viewType.getMappedType().getProperties(true);
assertEquals(1, properties.size());
final PropertyType attRef = properties.iterator().next();
assertTrue(attRef instanceof AttributeType);
assertNotEquals(baseType.getProperty("attRef"), attRef);
// test feature
final Feature baseFeature = baseType.newInstance();
baseFeature.setPropertyValue("attString", "hello world");
final Feature viewFeature = viewType.apply(baseFeature);
assertEquals("hello world", viewFeature.getPropertyValue("attRef"));
try {
viewFeature.getPropertyValue("attString");
fail("Property attString should not have been accessible");
} catch (PropertyNotFoundException ex) {
/*ok*/
}
}
use of org.geotoolkit.feature.ViewMapper in project geotoolkit by Geomatys.
the class DefaultJDBCFeatureStore method getQOMFeatureReader.
/**
* Get reader with geotk query model.
*/
private FeatureReader getQOMFeatureReader(final org.geotoolkit.storage.feature.query.Query query, Connection cnx) throws DataStoreException {
final String dbSchemaName = getDatabaseSchema();
final FeatureType type = dbmodel.getFeatureType(query.getTypeName());
final String tableName = type.getName().tip().toString();
TableMetaModel tableMeta = null;
if (dbSchemaName == null) {
// Try to handle empty schema name given at configuration
for (final SchemaMetaModel scheme : dbmodel.getSchemaMetaModels()) {
final TableMetaModel tableMetaTemp = scheme.getTable(tableName);
if (tableMetaTemp != null) {
tableMeta = tableMetaTemp;
break;
}
}
} else {
tableMeta = dbmodel.getSchemaMetaModel(getDatabaseSchema()).getTable(tableName);
}
if (tableMeta == null) {
throw new DataStoreException("Unable to get table " + tableName + " in the database.");
}
final FeatureType tableType = tableMeta.getType(TableMetaModel.View.ALLCOMPLEX).build();
final PrimaryKey pkey = dbmodel.getPrimaryKey(query.getTypeName());
// replace any PropertyEqualsTo in true ID filters
Filter baseFilter = query.getSelection();
baseFilter = (Filter) FIDFixVisitor.INSTANCE.visit(baseFilter);
// split the filter between what can be send and must be handle by code
final Filter[] divided = getDialect().splitFilter(baseFilter, tableType);
Filter preFilter = divided[0];
Filter postFilter = divided[1];
// ensure spatial filters are in featuretype geometry crs
preFilter = (Filter) new CRSAdaptorVisitor(tableType).visit(preFilter);
// rebuild a new query with the same params, but just the pre-filter
final org.geotoolkit.storage.feature.query.Query builder = new org.geotoolkit.storage.feature.query.Query();
builder.copy(query);
builder.setSelection(preFilter);
if (query.getResolution() != null) {
// attach resampling in hints; used later by postgis dialect
builder.getHints().add(new Hints(RESAMPLING, query.getResolution()));
}
final org.geotoolkit.storage.feature.query.Query preQuery = builder;
final FeatureType baseType = getFeatureType(query.getTypeName());
// Build the feature type returned by this query. Also build an eventual extra feature type
// containing the attributes we might need in order to evaluate the post filter
final FeatureType queryFeatureType;
final FeatureType returnedFeatureType;
if (query.retrieveAllProperties()) {
returnedFeatureType = queryFeatureType = (FeatureType) baseType;
} else {
// TODO BUG here, query with filter on a not returned geometry field crash
returnedFeatureType = (FeatureType) FeatureTypeExt.createSubType(tableType, query.getPropertyNames());
final FilterAttributeExtractor extractor = new FilterAttributeExtractor(tableType);
extractor.visit(postFilter, null);
final GenericName[] extraAttributes = extractor.getAttributeNames();
final List<GenericName> allAttributes = new ArrayList<>();
for (String str : query.getPropertyNames()) {
allAttributes.add(type.getProperty(str).getName());
}
for (GenericName extraAttribute : extraAttributes) {
if (!allAttributes.contains(extraAttribute)) {
allAttributes.add(extraAttribute);
}
}
// ensure we have the primarykeys
pkLoop: for (ColumnMetaModel pkc : pkey.getColumns()) {
final String pkcName = pkc.getName();
for (GenericName n : allAttributes) {
if (n.tip().toString().equals(pkcName)) {
continue pkLoop;
}
}
// add the pk attribut
allAttributes.add(baseType.getProperty(pkcName).getName());
}
final GenericName[] allAttributeArray = allAttributes.toArray(new GenericName[allAttributes.size()]);
queryFeatureType = (FeatureType) FeatureTypeExt.createSubType(tableType, allAttributeArray);
}
final String sql;
// we gave him the connection, he must not release it
final boolean release = (cnx == null);
if (cnx == null) {
try {
cnx = getDataSource().getConnection();
} catch (SQLException ex) {
throw new DataStoreException(ex.getMessage(), ex);
}
}
FeatureReader reader;
// so for now if we got one, we let the filter be evaluated in java and not with a sql query
if (containsOperation(preQuery, baseType)) {
try {
sql = getQueryBuilder().selectSQL(baseType, new org.geotoolkit.storage.feature.query.Query(baseType.getName()));
reader = new JDBCFeatureReader(this, sql, baseType, cnx, release, null);
FeatureStreams.subset(reader, query);
} catch (SQLException ex) {
throw new DataStoreException(ex.getMessage(), ex);
}
} else {
try {
sql = getQueryBuilder().selectSQL(queryFeatureType, preQuery);
reader = new JDBCFeatureReader(this, sql, queryFeatureType, cnx, release, null);
} catch (SQLException ex) {
throw new DataStoreException(ex.getMessage(), ex);
}
}
// if post filter, wrap it
if (postFilter != null && postFilter != Filter.include()) {
reader = FeatureStreams.filter(reader, postFilter);
}
// if we need to constraint type
if (!returnedFeatureType.equals(queryFeatureType)) {
reader = FeatureStreams.decorate(reader, new ViewMapper(type, query.getPropertyNames()), query.getHints());
}
return reader;
}
use of org.geotoolkit.feature.ViewMapper in project geotoolkit by Geomatys.
the class ViewFeatureTypeTest method filterAttributeTest.
@Test
public void filterAttributeTest() {
final FeatureTypeBuilder ftb = new FeatureTypeBuilder();
ftb.setName("test");
ftb.addAttribute(String.class).setName("attString");
ftb.addAttribute(Double.class).setName("attDouble");
final FeatureType baseType = ftb.build();
// test view type
final ViewMapper viewType = new ViewMapper(baseType, "attDouble");
final Collection<? extends PropertyType> properties = viewType.getMappedType().getProperties(true);
assertEquals(1, properties.size());
final PropertyType attDouble = properties.iterator().next();
assertEquals(baseType.getProperty("attDouble"), attDouble);
// test feature
final Feature baseFeature = baseType.newInstance();
baseFeature.setPropertyValue("attString", "hello world");
baseFeature.setPropertyValue("attDouble", 123.456);
final Feature viewFeature = viewType.apply(baseFeature);
assertEquals(123.456, (Double) viewFeature.getPropertyValue("attDouble"), 0);
try {
viewFeature.getPropertyValue("attString");
fail("Property attString should not have been accessible");
} catch (PropertyNotFoundException ex) {
/*ok*/
}
}
use of org.geotoolkit.feature.ViewMapper in project geotoolkit by Geomatys.
the class RetypeProcess method execute.
/**
* {@inheritDoc }
*/
@Override
protected void execute() {
final FeatureCollection inputFeatureList = inputParameters.getValue(VectorDescriptor.FEATURE_IN);
final FeatureType mask = inputParameters.getValue(RetypeDescriptor.MASK_IN);
final FeatureCollection resultFeatureList;
if (mask instanceof ViewMapper) {
resultFeatureList = FeatureStreams.decorate(inputFeatureList, (ViewMapper) mask);
} else {
resultFeatureList = inputFeatureList;
}
outputParameters.getOrCreate(VectorDescriptor.FEATURE_OUT).setValue(resultFeatureList);
}
Aggregations