⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 lockfeature.java

📁 电子地图服务器,搭建自己的地图服务
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
/* Copyright (c) 2001 - 2007 TOPP - www.openplans.org. All rights reserved.
 * This code is licensed under the GPL 2.0 license, availible at the root
 * application directory.
 */
package org.geoserver.wfs;

import net.opengis.wfs.AllSomeType;
import net.opengis.wfs.LockFeatureResponseType;
import net.opengis.wfs.LockFeatureType;
import net.opengis.wfs.LockType;
import net.opengis.wfs.WfsFactory;
import org.geotools.data.DataStore;
import org.geotools.data.DefaultQuery;
import org.geotools.data.DefaultTransaction;
import org.geotools.data.FeatureLock;
import org.geotools.data.FeatureLockFactory;
import org.geotools.data.FeatureLocking;
import org.geotools.data.FeatureSource;
import org.geotools.data.LockingManager;
import org.geotools.data.Query;
import org.geotools.data.Transaction;
import org.geotools.factory.CommonFactoryFinder;
import org.geotools.factory.GeoTools;
import org.geotools.feature.Feature;
import org.geotools.feature.FeatureCollection;
import org.opengis.filter.Filter;
import org.opengis.filter.FilterFactory;
import org.opengis.filter.FilterFactory2;
import org.opengis.filter.Id;
import org.opengis.filter.identity.FeatureId;
import org.opengis.referencing.crs.CoordinateReferenceSystem;
import org.vfny.geoserver.global.Data;
import org.vfny.geoserver.global.DataStoreInfo;
import org.vfny.geoserver.global.FeatureTypeInfo;
import java.io.IOException;
import java.math.BigInteger;
import java.util.HashSet;
import java.util.Iterator;
import java.util.List;
import java.util.Set;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.xml.namespace.QName;


/**
 * Web Feature Service 1.0 LockFeature Operation.
 *
 * @author Justin Deoliveira, The Open Planning Project
 *
 */
public class LockFeature {
    /**
     * The logger
     */
    static Logger LOGGER = org.geotools.util.logging.Logging.getLogger("org.geoserver.wfs");

    /**
     * Web Feature Service configuration
     */
    WFS wfs;

    /**
     * The catalog
     */
    Data catalog;

    /**
     * Filter factory
     */
    FilterFactory filterFactory;

    /**
     *
     * @param wfs
     * @param catalog
     */
    public LockFeature(WFS wfs, Data catalog) {
        this(wfs, catalog, null);
    }

    public LockFeature(WFS wfs, Data catalog, FilterFactory filterFactory) {
        this.wfs = wfs;
        this.catalog = catalog;
        this.filterFactory = filterFactory;
    }

    public void setFilterFactory(FilterFactory filterFactory) {
        this.filterFactory = filterFactory;
    }

    /**
     * Locks features according to the request.
     *
     * @param request
     * @return the WFS 1.1 required response
     * @throws WFSException
     *             if a lock failed and the lock specified all locks, or if an
     *             another error occurred processing the lock operation
     */
    public LockFeatureResponseType lockFeature(LockFeatureType request)
        throws WFSException {
        FeatureLock fLock = null;

        try {
            // check we are dealing with a well formed request, there is at
            // least on lock request?
            List locks = request.getLock();

            if ((locks == null) || locks.isEmpty()) {
                String msg = "A LockFeature request must contain at least one LOCK element";
                throw new WFSException(msg);
            }

            LOGGER.info("locks size is " + locks.size());

            // create a new lock (token used to manage locks across datastores)
            fLock = newFeatureLock(request);

            // prepare the response object
            LockFeatureResponseType response = WfsFactory.eINSTANCE.createLockFeatureResponseType();
            response.setLockId(fLock.getAuthorization());
            response.setFeaturesLocked(WfsFactory.eINSTANCE.createFeaturesLockedType());
            response.setFeaturesNotLocked(WfsFactory.eINSTANCE.createFeaturesNotLockedType());

            // go thru each lock request, and try to perform locks on a feature
            // by feature basis
            // in order to allow for both "all" and "some" lock behaviour
            // TODO: if the lock is the default this default, lock the whole
            // query directly, should be a lot faster
            for (int i = 0, n = locks.size(); i < n; i++) {
                LockType lock = (LockType) locks.get(i);
                LOGGER.info("curLock is " + lock);

                QName typeName = lock.getTypeName();

                // get out the filter, and default to no filtering if none was
                // provided
                Filter filter = (Filter) lock.getFilter();

                if (filter == null) {
                    filter = Filter.INCLUDE;
                } 

                FeatureTypeInfo meta;
                FeatureSource source;
                FeatureCollection features;

                try {
                    meta = catalog.getFeatureTypeInfo(typeName.getLocalPart(),
                            typeName.getNamespaceURI());

                    if (meta == null) {
                        throw new WFSException("Unknown feature type " + typeName.getPrefix() + ":"
                            + typeName.getLocalPart());
                    }

                    source = meta.getFeatureSource();
                    
                    // make sure all geometric elements in the filter have a crs, and that the filter
                    // is reprojected to store's native crs as well
                    CoordinateReferenceSystem declaredCRS = WFSReprojectionUtil.getDeclaredCrs(
                            source.getSchema(), request.getVersion());
                    filter = WFSReprojectionUtil.normalizeFilterCRS(filter, source.getSchema(), declaredCRS);
                    
                    // now gather the features
                    features = source.getFeatures(filter);

                    if (source instanceof FeatureLocking) {
                        ((FeatureLocking) source).setFeatureLock(fLock);
                    }
                } catch (IOException e) {
                    throw new WFSException(e);
                }

                Iterator reader = null;
                int numberLocked = -1;

                try {
                    for (reader = features.iterator(); reader.hasNext();) {
                        Feature feature = (Feature) reader.next();

                        FeatureId fid = fid(feature.getID());
                        Id fidFilter = fidFilter(fid);

                        if (!(source instanceof FeatureLocking)) {
                            LOGGER.fine("Lock " + fid + " not supported by data store (authID:"
                                + fLock.getAuthorization() + ")");

                            response.getFeaturesNotLocked().getFeatureId().add(fid);

                            // lockFailedFids.add(fid);
                        } else {
                            // DEFQuery is just some indirection, should be in
                            // the locking interface.
                            // int numberLocked =
                            // ((DEFQueryFeatureLocking)source).lockFeature(feature);
                            // HACK: Query.NO_NAMES isn't working in postgis
                            // right now,
                            // so we'll just use all.
                            Query query = new DefaultQuery(meta.getTypeName(), (Filter) fidFilter,
                                    Query.DEFAULT_MAX, Query.ALL_NAMES, lock.getHandle());

                            numberLocked = ((FeatureLocking) source).lockFeatures(query);

                            if (numberLocked == 1) {
                                LOGGER.fine("Lock " + fid + " (authID:" + fLock.getAuthorization()
                                    + ")");
                                response.getFeaturesLocked().getFeatureId().add(fid);

                                // lockedFids.add(fid);
                            } else if (numberLocked == 0) {
                                LOGGER.fine("Lock " + fid + " conflict (authID:"
                                    + fLock.getAuthorization() + ")");
                                response.getFeaturesNotLocked().getFeatureId().add(fid);

                                // lockFailedFids.add(fid);
                            } else {
                                LOGGER.warning("Lock " + numberLocked + " " + fid + " (authID:"
                                    + fLock.getAuthorization() + ") duplicated FeatureID!");
                                response.getFeaturesLocked().getFeatureId().add(fid);

                                // lockedFids.add(fid);
                            }
                        }
                    }
                } catch (IOException ioe) {
                    throw new WFSException(ioe);
                } finally {
                    if (reader != null) {
                        features.close(reader);
                    }
                }

                // refresh lock times, so they all start the same instant and we
                // are nearer
                // to the spec when it says the expiry should start when the
                // lock
                // feature response has been totally written
                if (numberLocked > 0) {
                    Transaction t = new DefaultTransaction();

                    try {
                        try {
                            t.addAuthorization(response.getLockId());
                            source.getDataStore().getLockingManager()
                                  .refresh(response.getLockId(), t);
                        } finally {
                            t.commit();
                        }
                    } catch (IOException e) {
                        throw new WFSException(e);
                    }
                }
            }

            // should we releas all? if not set default to true
            boolean lockAll = !(request.getLockAction() == AllSomeType.SOME_LITERAL);

            if (lockAll && !response.getFeaturesNotLocked().getFeatureId().isEmpty()) {
                // I think we need to release and fail when lockAll fails
                //
                // abort will release the locks

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -