Package org.geoserver.catalog

Source Code of org.geoserver.catalog.StructuredCoverageViewReader$GranuleStoreView

/* (c) 2014 Open Source Geospatial Foundation - all rights reserved
* (c) 2014 OpenPlans
* This code is licensed under the GPL 2.0 license, available at the root
* application directory.
*/
package org.geoserver.catalog;

import java.io.IOException;
import java.util.Collection;
import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;

import org.geoserver.catalog.CoverageView.CoverageBand;
import org.geotools.coverage.grid.io.DimensionDescriptor;
import org.geotools.coverage.grid.io.GranuleSource;
import org.geotools.coverage.grid.io.GranuleStore;
import org.geotools.coverage.grid.io.HarvestedSource;
import org.geotools.coverage.grid.io.StructuredGridCoverage2DReader;
import org.geotools.data.DataUtilities;
import org.geotools.data.Query;
import org.geotools.data.Transaction;
import org.geotools.data.collection.ListFeatureCollection;
import org.geotools.data.simple.SimpleFeatureCollection;
import org.geotools.factory.Hints;
import org.geotools.feature.SchemaException;
import org.geotools.feature.collection.AbstractFeatureVisitor;
import org.geotools.gce.imagemosaic.Utils;
import org.geotools.geometry.jts.ReferencedEnvelope;
import org.geotools.util.DefaultProgressListener;
import org.opengis.feature.Feature;
import org.opengis.feature.Property;
import org.opengis.feature.simple.SimpleFeature;
import org.opengis.feature.simple.SimpleFeatureType;
import org.opengis.feature.type.AttributeDescriptor;
import org.opengis.feature.type.Name;
import org.opengis.filter.Filter;

/**
* A coverageView reader using a structured coverage readers implementation
*
* @author Daniele Romagnoli - GeoSolutions
*/
public class StructuredCoverageViewReader extends CoverageViewReader implements
        StructuredGridCoverage2DReader {

    private final static Logger LOGGER = org.geotools.util.logging.Logging
            .getLogger(StructuredCoverageViewReader.class);

    static class GranuleStoreView implements GranuleStore {

        private StructuredGridCoverage2DReader reader;

        private CoverageView coverageView;

        private String name;

        private boolean readOnly;

        private SimpleFeatureType schema;

        public GranuleStoreView(StructuredGridCoverage2DReader structuredDelegate,
                String referenceName, CoverageView coverageView, boolean readOnly)
                throws UnsupportedOperationException, IOException {
            this.reader = structuredDelegate;
            this.coverageView = coverageView;
            this.name = referenceName;
            this.readOnly = readOnly;
            this.schema = buildSchema();
        }

        private SimpleFeatureType buildSchema() throws IOException {
            GranuleSource source = reader.getGranules(name, readOnly);
            SimpleFeatureType inputSchema = source.getSchema();
            List<AttributeDescriptor> descriptors = inputSchema.getAttributeDescriptors();
            StringBuilder builder = new StringBuilder();
            for (AttributeDescriptor descriptor : descriptors) {

                // Avoid exposing ImageIndex
                if (!descriptor.getLocalName().equalsIgnoreCase("imageIndex")) {
                    Class<?> binding = descriptor.getType().getBinding();
                    String bindingClass = binding.toString();
                    if (bindingClass.startsWith("class ")) {
                        bindingClass = bindingClass.substring(6, bindingClass.length());
                    }

                    builder.append(descriptor.getName()).append(":").append(bindingClass)
                            .append(",");
                }
            }
            String schema = builder.toString();
            schema = schema.substring(0, schema.length() - 1);

            try {
                return DataUtilities.createType(coverageView.getName(), schema);
            } catch (SchemaException e) {
                throw new IOException("Exception occurred while creating the schemaType", e);
            }
        }

        @Override
        public SimpleFeatureCollection getGranules(Query q) throws IOException {
            List<CoverageBand> bands = coverageView.getCoverageBands();
            SimpleFeatureCollection collection = null;
            for (CoverageBand band : bands) {
                String coverageName = band.getInputCoverageBands().get(0).getCoverageName();
                if (collection == null) {
                    collection = reader.getGranules(coverageName, readOnly).getGranules(q);
                } else {
                    collection = join(collection, band, coverageName);
                }
            }
            return collection;
        }

        private SimpleFeatureCollection join(SimpleFeatureCollection inputCollection,
                CoverageBand band, final String coverageName) throws IOException {
            // TODO Improve this by doing batch join and storing the result into memory

            final DefaultProgressListener listener = new DefaultProgressListener();
            final ListFeatureCollection collection = new ListFeatureCollection(schema);
            // Getting attributes structure to be filled

            inputCollection.accepts(new AbstractFeatureVisitor() {
                public void visit(Feature feature) {
                    if (feature instanceof SimpleFeature) {
                        // get the feature
                        final SimpleFeature sourceFeature = (SimpleFeature) feature;
                        Collection<Property> props = sourceFeature.getProperties();
                        Name propName = null;
                        Object propValue = null;

                        // Assigning value to dest feature for matching attributes
                        Filter filter = null;
                        for (Property prop : props) {
                            propName = prop.getName();
                            if (
                            !propName.getLocalPart().equalsIgnoreCase("imageIndex")
                                    && !propName.getLocalPart().equalsIgnoreCase("the_geom")
                                    && !propName.getLocalPart().equalsIgnoreCase("location")) {
                                propValue = prop.getValue();
                                Filter updatedFilter = Utils.FF.equal(Utils.FF.property(propName),
                                        Utils.FF.literal(propValue), true);
                                if (filter == null) {
                                    filter = updatedFilter;
                                } else {
                                    filter = FF.and(filter, updatedFilter);
                                }
                            }
                        }
                        Query query = new Query();
                        query.setFilter(filter);
                        SimpleFeatureCollection coverageCollection;
                        try {
                            coverageCollection = reader.getGranules(coverageName, readOnly)
                                    .getGranules(query);
                            coverageCollection.accepts(new AbstractFeatureVisitor() {
                                public void visit(Feature feature) {
                                    if (feature instanceof SimpleFeature) {
                                        // get the feature
                                        final SimpleFeature destFeature = DataUtilities
                                                .template(schema);
                                        Collection<Property> props = destFeature.getProperties();
                                        Name propName = null;
                                        Object propValue = null;

                                        // Assigning value to dest feature for matching attributes
                                        for (Property prop : props) {
                                            propName = prop.getName();
                                            propValue = ((SimpleFeature) feature)
                                                    .getAttribute(propName);
                                            // Matching attributes are set

                                            destFeature.setAttribute(propName, propValue);
                                        }
                                        collection.add(destFeature);

                                        // check if something bad occurred
                                        if (listener.isCanceled() || listener.hasExceptions()) {
                                            if (listener.hasExceptions())
                                                throw new RuntimeException(listener.getExceptions()
                                                        .peek());
                                            else
                                                throw new IllegalStateException(
                                                        "Feature visitor has been canceled");
                                        }
                                    }
                                }
                            }, listener);
                        } catch (IOException e) {
                            LOGGER.log(Level.FINER, e.getMessage(), e);
                        } catch (UnsupportedOperationException e) {
                            LOGGER.log(Level.FINER, e.getMessage(), e);
                        }

                        // check if something bad occurred
                        if (listener.isCanceled() || listener.hasExceptions()) {
                            if (listener.hasExceptions())
                                throw new RuntimeException(listener.getExceptions().peek());
                            else
                                throw new IllegalStateException("Feature visitor has been canceled");
                        }
                    }
                }
            }, listener);

            return collection;
        }

        @Override
        public int getCount(Query q) throws IOException {
            return getGranules(q).size();
        }

        @Override
        public ReferencedEnvelope getBounds(Query q) throws IOException {
            return getGranules(q).getBounds();
        }

        @Override
        public SimpleFeatureType getSchema() throws IOException {
            return schema;
        }

        @Override
        public void dispose() throws IOException {
            // TODO: check if we need to dispose it or not
            // Does nothing, the catalog should be disposed by the user
        }

        @Override
        public void addGranules(SimpleFeatureCollection granules) {
            // We deal with the one from the underlying reader
            throw new UnsupportedOperationException();
        }

        @Override
        public int removeGranules(Filter filter) {
            List<CoverageBand> bands = coverageView.getCoverageBands();
            int removed = 0;
            for (CoverageBand band : bands) {
                String coverageName = band.getInputCoverageBands().get(0).getCoverageName();
                GranuleStore granuleStore;
                try {
                    granuleStore = (GranuleStore) reader.getGranules(coverageName, false);
                    // TODO: We may revisit the #removed granules computation to take into
                    // account cases where we remove different number of records across different
                    // input coverages
                    removed = granuleStore.removeGranules(filter);
                } catch (UnsupportedOperationException e) {
                    LOGGER.log(Level.FINER, e.getMessage(), e);
                } catch (IOException e) {
                    LOGGER.log(Level.FINER, e.getMessage(), e);
                }
            }
            return removed;
        }

        @Override
        public void updateGranules(String[] attributeNames, Object[] attributeValues, Filter filter) {
            throw new UnsupportedOperationException();
        }

        @Override
        public Transaction getTransaction() {
            return null;
        }

        @Override
        public void setTransaction(Transaction transaction) {

        }
    }

    private StructuredGridCoverage2DReader structuredDelegate;

    public StructuredCoverageViewReader(StructuredGridCoverage2DReader delegate,
            CoverageView coverageView, CoverageInfo coverageInfo, Hints hints) {
        super(delegate, coverageView, coverageInfo, hints);
        structuredDelegate = delegate;
    }

    @Override
    public GranuleSource getGranules(String coverageName, boolean readOnly) throws IOException,
            UnsupportedOperationException {
        return new GranuleStoreView(structuredDelegate, referenceName, coverageView, readOnly);
    }

    @Override
    public boolean isReadOnly() {
        return structuredDelegate.isReadOnly();
    }

    @Override
    public void createCoverage(String coverageName, SimpleFeatureType schema) throws IOException,
            UnsupportedOperationException {
        throw new UnsupportedOperationException("Operation unavailable for Coverage Views");
    }

    @Override
    public boolean removeCoverage(String coverageName) throws IOException,
            UnsupportedOperationException {
        return removeCoverage(referenceName, false);
    }

    @Override
    public boolean removeCoverage(String coverageName, boolean delete) throws IOException,
            UnsupportedOperationException {
        throw new UnsupportedOperationException("Operation unavailable for Coverage Views");
    }

    @Override
    public void delete(boolean deleteData) throws IOException {
        structuredDelegate.delete(deleteData);
    }

    @Override
    public List<HarvestedSource> harvest(String defaultTargetCoverage, Object source, Hints hints)
            throws IOException, UnsupportedOperationException {
        return structuredDelegate.harvest(defaultTargetCoverage, source, hints);
    }

    @Override
    public List<DimensionDescriptor> getDimensionDescriptors(String coverageName)
            throws IOException {
        return structuredDelegate.getDimensionDescriptors(referenceName);
    }
}
TOP

Related Classes of org.geoserver.catalog.StructuredCoverageViewReader$GranuleStoreView

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.